为什么java.util.Observable不是一个抽象类?
2022-08-31 20:02:35
我刚刚注意到java.util.Observable是一个具体的类。由于 Observable 的目的是扩展,这在我看来很奇怪。为什么以这种方式实现它?
我发现这篇文章说
可观察量是一个具体的类,因此必须预先确定从它派生的类,因为Java只允许单继承。
但这并不能真正向我解释。事实上,如果 Observable 是抽象的,则用户将被迫确定从它派生的类。
我刚刚注意到java.util.Observable是一个具体的类。由于 Observable 的目的是扩展,这在我看来很奇怪。为什么以这种方式实现它?
我发现这篇文章说
可观察量是一个具体的类,因此必须预先确定从它派生的类,因为Java只允许单继承。
但这并不能真正向我解释。事实上,如果 Observable 是抽象的,则用户将被迫确定从它派生的类。
很简单,Observable是一个抽象的或其他类,这是一个错误。
Observable
应该是一个接口,JDK应该提供一个方便的实现(就像一个接口,是一个实现)List
ArrayList
Java中有很多“错误”,包括:
Arrays.toString(array)
toString()
可克隆
不应该是一个标记接口;它应该有方法,Object.clone()
不应该存在clone()
在肥皂盒上,就语言本身而言,恕我直言:
==
应该执行该方法(这会导致大量头痛).equals()
==
===
boolean isIdentical(Object o)
<
应为对象执行(类似地对 、 、compareTo(Object o) < 0
Comparable
>
<=
>=
)作为第一种方法,人们可以认为这样做是为了允许用户使用组合而不是继承,如果您的类已经从另一个类继承,并且您也不能从可观察类继承,这将非常方便。
但是,如果我们查看Observable的源代码,我们会看到有一个内部标志。
private boolean changed = false;
每次调用 notifyObservers 时都会检查这一点:
public void notifyObservers(Object arg) {
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);
}
但是从这个 Observable 组成的类中,我们无法更改此标志,因为它是私有的,并且提供用于更改它的方法受到保护。
这意味着用户被迫对 Observable 类进行子类类,我会说缺少“abstract”关键字只是一个“错误”。
我会说这门课完全是搞砸了。