【发布时间】:2016-02-02 19:57:18
【问题描述】:
我正在通过tutorial 学习并尝试在 Java 中实现观察者模式。我一直纠结于是否应该使用WeakReference 来让主题保持观察者。
对于下面的实现,Subject 和 BinaryObserver 相互持有强引用,这恐怕会阻止 GC 收集未使用的 Subject。
所以我的问题是,我应该使用List<WeakReference<Observer>> observers 而不是List<Observer> observers?
Subject.java
public class Subject {
private List<Observer> observers = new ArrayList<Observer>();
private int state;
public int getState() {
return state;
}
public void setState(int state) {
this.state = state;
notifyAllObservers();
}
public void attach(Observer observer){
observers.add(observer);
}
public void notifyAllObservers(){
for (Observer observer : observers) {
observer.update();
}
}
}
Observer.java
public abstract class Observer {
protected Subject subject;
public abstract void update();
}
BinaryObserver.java
public class BinaryObserver extends Observer{
public BinaryObserver(Subject subject){
this.subject = subject;
this.subject.attach(this);
}
@Override
public void update() {
System.out.println("Binary String: " + Integer.toBinaryString());
}
}
ObserverPatternDemo.java
public class ObserverPatternDemo {
public static void main(String[] args) {
Subject subject = new Subject();
new BinaryObserver(subject);
System.out.println("First state change: 15");
subject.setState(15);
}
}
【问题讨论】:
-
弱引用是邪恶的,只有在你喜欢追逐错误时才使用它们。注意:Java 的 GC 很聪明
-
让我修改@SleimanJneidi 的声明:Java 的 GC 非常非常智能。它基于“可达性”工作 - 如果
Subject和Observer都不是“可达性”(本质上:无法从任何以main()方法中的对象开头的对象引用链访问它们) ,然后可以收集它们。它们相互引用并不重要。这些引用仅确保如果一个是可访问的,那么另一个也是。如果两者都无法到达,它不会不必要地让它们保持活力。 -
谢谢~但是我们什么时候应该使用
WeakReference?我认为观察者模式是WeakReference的一个很好的例子,因为在 C++ 中 oberser 模式是weak_ptr的一个很好的例子... -
@Hackjustu 如果你希望你的程序依赖于 GC 的行为而变得不可预测,你可以使用 WeakReference
-
相信 GC。如果您关心性能,不如尝试不同的配置:gc 的类型(g1、parallel、...)、young gen 空间等。
标签: java design-patterns