以下简单的代码片段工作正常,并使用null对象访问静态字段.
final class TestNull
{
public static int field=100;
public TestNull temp()
{
return(null);
}
}
public class Main
{
public static void main(String[] args)
{
System.out.println(new TestNull().temp().field);
}
}
Run Code Online (Sandbox Code Playgroud)
在上面的代码中,System.out.println(new TestNull().temp().field);静态字段字段与NULL对象关联的语句new TestNull().temp()仍然返回正确的值100,而不是在Java中抛出空指针异常!为什么?
aio*_*obe 12
与常规成员变量相反,静态变量属于类,而不属于类的实例.它的工作原因仅仅是因为您不需要实例来访问静态字段.
事实上,如果访问一个静态字段可能会抛出一个,我会更加惊讶NullPointerException.
如果你很好奇,这里的字节码代表你的程序:
// Create TestNull object
3: new #3; //class TestNull
6: dup
7: invokespecial #4; //Method TestNull."<init>":()V
// Invoke the temp method
10: invokevirtual #5; //Method TestNull.temp:()LTestNull;
// Discard the result of the call to temp.
13: pop
// Load the content of the static field.
14: getstatic #6; //Field TestNull.field:I
Run Code Online (Sandbox Code Playgroud)
这在Java语言规范的第15.11.1节:使用主节点的字段访问中进行了描述.他们甚至提供了一个例子:
以下示例演示了可以使用null引用来访问类(静态)变量而不会导致异常:
Run Code Online (Sandbox Code Playgroud)class Test { static String mountain = "Chocorua"; static Test favorite(){ System.out.print("Mount "); return null; } public static void main(String[] args) { System.out.println(favorite().mountain); } }它编译,执行和打印:
Chocorua山
静态变量在类的每个对象之间共享.因此,当您返回的实际对象引用为null时(在C++中:TestNull*temp = null;),您有一个TestNull类型的对象,Java可以使用它来查找该类的静态值.
请记住,Java对象确实是指针.指针有一种类型.从那种类型,Java可以识别某些信息,即使它指向null.