xqw的个人博客

Posted on By xqw

  • content {:toc}

观察者模式

建立对象与对象之间的依赖关系,一个被观察者发生改变,将通知其他观察者
需求:用户关注商品,商品价格发生改变通知用户
JDK java.util有Observer接口和抽象类Observable

//抽象主题、被观察者
public class Observable {
    private boolean changed = false;
    private Vector<Observer> obs;

    public synchronized void addObserver(Observer o) {
        if (o == null)
            throw new NullPointerException();
        if (!obs.contains(o)) {
            obs.addElement(o);
        }
    }

    public synchronized void deleteObserver(Observer o) {
        obs.removeElement(o);
    }

    public void notifyObservers(Object arg) {
        /*
         * a temporary array buffer, used as a snapshot of the state of
         * current Observers.
         */
        Object[] arrLocal;

        synchronized (this) {
            if (!changed)
                return;
            arrLocal = obs.toArray();
            clearChanged();
        }

        for (int i = arrLocal.length - 1; i >= 0; i--)
            ((Observer) arrLocal[i]).update(this, arg);
    }
.......

    //抽象观察者接口
    public interface Observer {
        /**
         * This method is called whenever the observed object is changed. An
         * application calls an <tt>Observable</tt> object's
         * <code>notifyObservers</code> method to have all the object's
         * observers notified of the change.
         *
         * @param   o     the observable object.
         * @param   arg   an argument passed to the <code>notifyObservers</code>
         *                 method.
         */
        void update(Observable o, Object arg);
    }
//商品类实现类--被观察者、主题
public class Item extends Observable {
    private String name;
    private double price;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public double getPrice() {
        return price;
    }

    public void setPrice(double price) {
        this.price = price;
        //发生改变
        this.setChanged();
        //通知被观察者
        this.notifyObservers(price);
    }
}
//用户-- 观察者
public class User implements Observer {
    private String name;

    public User(String name) {
        this.name = name;
    }

    //其他password等,setter省略
    @Override
    public void update(Observable o, Object arg) {
        if (arg instanceof Double) {
            System.out.println("价格改变了,变成" + arg);
        }
    }
}
//测试
public class ObserveTest {
    public static void main(String[] args) {
        Item it = new Item();
        it.setName("手机");
        it.setPrice(2299.0D);
        User user = new User("张三");
        it.addObserver(user);
        it.setPrice(2099.0D);
    }
}

价格改变了,变成2099.0

策略模式

改善实际编码中if switch过多的语句,并且增加复用性、利于维护
需求:将卖家排序,根据销售量、价格、人气不同策略对数据库结果进行排序

//卖家
public class Seller {
    private int sale;
    private int popular;
    private double price;
    //省略getset
}
//抽象策略类,java.util.Comparator包中
public interface Comparator<T> {
    int compare(T o1, T o2);
}
//具体策略类
//1根据销售量排序
public class SaleComparator implements Comparator<Seller> {
    @Override
    public int compare(Seller o1, Seller o2) {
        Integer d1 = o1.getSale();
        Integer d2 = o2.getSale();
        return d1.compareTo(d2);
    }
}

//2根据价格排序
public class PriceComparator implements Comparator<Seller> {
    @Override
    public int compare(Seller o1, Seller o2) {
        Double d1 = o1.getPrice();
        Double d2 = o2.getPrice();
        return d1.compareTo(d2);
    }
}
//根据不同策略排序--具体策略类
public class SellerSort {
    public static List<Seller> sort(List<Seller> items, Comparator<Seller> c) {
        Collections.sort(items, c);
        return items;
    }
}