这两种初始化观察者ArrayList的方法有什么区别。或者任何其他类型的事情。一个比另一个快吗?或者我在这里错过了其他一些好处。
class Publisher implements Observerable
{
private ArrayList observers = new ArrayList();
}
class Publisher implements Observerable
{
private ArrayList observers;
public Publisher()
{
observers = new ArrayList();
}
}
答案 0 :(得分:13)
他们是等同的。实际上,如果你编译这两个,你会看到它们生成完全相同的字节代码:
Publisher();
Code:
0: aload_0
1: invokespecial #1; //Method java/lang/Object."<init>":()V
4: aload_0
5: new #2; //class java/util/ArrayList
8: dup
9: invokespecial #3; //Method java/util/ArrayList."<init>":()V
12: putfield #4; //Field observers:Ljava/util/ArrayList;
15: return
}
鉴于它们是相同的代码,显然不会有任何速度差异:)
请注意,在C#中,它们并不完全相同 - 在C#中,observers
的初始化程序将在基础构造函数调用之前运行;在Java中他们真的是一样的。
你使用的是品味问题。如果你有几个不同的构造函数,它们都以相同的方式初始化变量,那么使用第一个表单是有意义的。另一方面,如果你有几个构造函数试图让大多数构造函数调用一个“核心”构造函数来完成实际工作,那么通常是一个好主意。
答案 1 :(得分:4)
他们是平等的,但是: 不同之处在于,在上一个示例中,您可以获得能够执行更高级初始化逻辑的好处:错误处理等。
答案 2 :(得分:2)
唯一真正的区别在于操作顺序。在调用类的构造函数之前,将评估在其声明中初始化的字段。以这种方式在子类中初始化的字段将在super的构造函数完成之后但在调用子类的构造函数之前进行计算。
考虑以下示例:
我有一个测试类:
public class Tester {
Tester (String msg) {
System.out.println(this + ":" + msg);
}
}
我有一个超级班:
public class Test {
protected Tester t1 = new Tester("super init block");
Test (String constructorMsg) {
new Tester(constructorMsg);
}
}
我有一个子类:
Public class TestSub extends Test {
private Tester t2 = new Tester("sub init block");
TestSub(String constructorMsg) {
super(constructorMsg);
new TTester("sub constructor");
}
}
在我的main
方法中,我创建了TestSub
的实例:
public static void main(String[] args) {
new TestSub("super constructor");
}
结果如下:
Tester@3e205f:super init block
Tester@bf73fa:super constructor
Tester@5740bb:sub init block
Tester@5ac072:sub constructor
答案 3 :(得分:1)
没有任何区别。第一种方式的优点是,如果您有多个构造函数,则无需记住在所有构造函数中初始化observers
。
在第二个示例中,如果要根据构造函数的参数调整值,则可以更灵活。