简体   繁体   中英

How am I able to call a method on a null object?

public class JavaPuzzler {

    public static void main(String[] args) {
    JavaPuzzler javaPuzzler = null;
    System.out.println(javaPuzzler.get());
    }

    private static String get(){
        return "i am a java puzzler";
    }
}

You might think that it should throw NullPointerException because the main method invokes get() method on local variable which is initialized to null , and you can't invoke a method on null.

But if you run this program, you will see that it prints “i am a java puzzler”.

Can anybody give me the answer. Thanks in advance.

In your code sample, get() is a static member that belongs to the class, not to an instance. You do not need an instance in order to invoke the method.

public static String get() // belongs globally to class, no instance required
public String get() // belongs to instance

It's because the method is static and though you reference an instance, the instance isn't necessary. The Java Language Specification explains why in section 8.4.3.2 :

A method that is declared static is called a class method. A class method is always invoked without reference to a particular object.

This means that it does not matter if javaPuzzler instance is null - the method "belongs" to the class, not an instance.

get方法是静态的,这意味着在该调用中忽略了javaPuzzler中的实际引用,只使用了变量的类型。

Your method is static. So it could only be called in a static way.

So even though you are putting it as javaPuzzler.get(), actual call will be JavaPuzzler.get() and thus the printing!!

你正在调用一个静态方法,你不需要一个实例来调用它,这就是它的工作原理。

If we try calling a method using NULL object it will throw NullPointerException as long as the method is not static.

If method is static it will run.

Read HERE for more reference

Like everyone mentions here, it works because get() is a static method. Here's a way that you can think about this:

When you define a class in Java, what you're essentially doing is defining the data that an object will hold, and a set of methods that operate on that data. Now while you can have thousands and thousands of objects, it doesn't make sense to have copies of all the methods for each of them. What happens is that the class stores the methods you define, and executes them in the scope of the object that you call the method on. If you attempt to call these methods on an uninitialized object, the object still exists and the method still exists, but it has no valid to scope to work on, thus giving you the NullPointerException .

The exception to this rule is static methods, which are methods that don't need a scope - they don't refer to object-specific data. This is why they can run irrespective of whether the object is initialized or not.

Just remember that objects don't have copies of their methods... the methods are just called in the scope of the object's data. So you can still access the methods of null (uninitialized) objects, but non-static methods have no data to work on.

In the above code you have given get() function as static. Static functions and data members do no belong to any object. They belong to the class. You can call static function using object of class but thats not a good approach as it consumes extra memory.

Since static, JavaPuzzler.get()); will give you the output and not null pointer exception.

It would have given null pointer exception in case the get() method would have been non static.

The compiler changes the instance call to a class call automatically. If you have a decompiler you can observe the change in the generated byte code:

...
 public static main([Ljava/lang/String;)V
   L0
    LINENUMBER 8 L0
    ACONST_NULL
    ASTORE 1
   L1
    LINENUMBER 9 L1
    GETSTATIC java/lang/System.out : Ljava/io/PrintStream;
    INVOKESTATIC JavaPuzzler.get()Ljava/lang/String;
    INVOKEVIRTUAL java/io/PrintStream.println(Ljava/lang/String;)V
   L2
    LINENUMBER 11 L2
    RETURN
   L3
    LOCALVARIABLE args [Ljava/lang/String; L0 L3 0
    LOCALVARIABLE javaPuzzler LJavaPuzzler; L1 L3 1
    MAXSTACK = 2
    MAXLOCALS = 2
...

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM