Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
162 views
in Technique[技术] by (71.8m points)

java - 什么是NullPointerException,我该如何解决?(What is a NullPointerException, and how do I fix it?)

What are Null Pointer Exceptions ( java.lang.NullPointerException ) and what causes them?

(什么是空指针异常( java.lang.NullPointerException ),是什么导致它们?)

What methods/tools can be used to determine the cause so that you stop the exception from causing the program to terminate prematurely?

(可以使用哪些方法/工具确定原因,以阻止异常导致程序过早终止?)

  ask by community wiki translate from so

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

When you declare a reference variable (ie an object) you are really creating a pointer to an object.

(声明引用变量(即对象)时,实际上是在创建指向对象的指针。)

Consider the following code where you declare a variable of primitive type int :

(考虑以下代码,在其中声明基本类型为int的变量:)

int x;
x = 10;

In this example, the variable x is an int and Java will initialize it to 0 for you.

(在此示例中,变量x是一个int ,Java会为您将其初始化为0 。)

When you assign it the value of 10 on the second line, your value of 10 is written into the memory location referred to by x .

(在第二行为其分配值10时,会将值10写入x所指的内存位置。)

But, when you try to declare a reference type , something different happens.

(但是,当您尝试声明引用类型时 ,会发生一些不同的事情。)

Take the following code:

(采取以下代码:)

Integer num;
num = new Integer(10);

The first line declares a variable named num , but it does not actually contain a primitive value yet.

(第一行声明了一个名为num的变量,但实际上尚未包含原始值。)

Instead, it contains a pointer (because the type is Integer which is a reference type).

(相反,它包含一个指针(因为类型是Integer ,它是引用类型)。)

Since you have not yet said what to point to, Java sets it to null , which means " I am pointing to nothing ".

(由于您尚未说出要指向的内容,因此Java将其设置为null ,这意味着“ 什么都没有指向 ”。)

In the second line, the new keyword is used to instantiate (or create) an object of type Integer and the pointer variable num is assigned to that Integer object.

(在第二行中, new关键字用于实例化(或创建) Integer类型的对象,并将指针变量num分配给该Integer对象。)

The NullPointerException occurs when you declare a variable but did not create an object.

(当您声明变量但未创建对象时,会发生NullPointerException 。)

So you are pointing to something that does not actually exist.

(因此,您指向的是实际上不存在的东西。)

If you attempt to dereference num BEFORE creating the object you get a NullPointerException .

(如果在创建对象之前尝试取消引用num ,则会收到NullPointerException 。)

In the most trivial cases, the compiler will catch the problem and let you know that " num may not have been initialized ," but sometimes you may write code that does not directly create the object.

(在大多数情况下,编译器会捕获该问题,并告知您“ num may not have been initialized ”,但是有时您可能会编写不直接创建该对象的代码。)

For instance, you may have a method as follows:

(例如,您可能具有如下方法:)

public void doSomething(SomeObject obj) {
   //do something to obj
}

In which case, you are not creating the object obj , but rather assuming that it was created before the doSomething() method was called.

(在这种情况下,您不是在创建对象obj ,而是假设它是在调用doSomething()方法之前创建的。)

Note, it is possible to call the method like this:

(注意,可以这样调用方法:)

doSomething(null);

In which case, obj is null .

(在这种情况下, objnull 。)

If the method is intended to do something to the passed-in object, it is appropriate to throw the NullPointerException because it's a programmer error and the programmer will need that information for debugging purposes.

(如果该方法旨在对传入的对象做一些事情,则抛出NullPointerException是适当的,因为它是程序员的错误,程序员将需要该信息来进行调试。)

Alternatively, there may be cases where the purpose of the method is not solely to operate on the passed in object, and therefore a null parameter may be acceptable.

(替代地,在某些情况下,该方法的目的不仅是要对传入的对象进行操作,因此null参数是可以接受的。)

In this case, you would need to check for a null parameter and behave differently.

(在这种情况下,您将需要检查null参数并改变行为。)

You should also explain this in the documentation.

(您还应该在文档中对此进行解释。)

For example, doSomething() could be written as:

(例如, doSomething()可以写为:)

/**
  * @param obj An optional foo for ____. May be null, in which case 
  *  the result will be ____.
  */
public void doSomething(SomeObject obj) {
    if(obj != null) {
       //do something
    } else {
       //do something else
    }
}

Finally, How to pinpoint the exception & cause using Stack Trace

(最后, 如何使用堆栈跟踪来查明异常和原因)

What methods/tools can be used to determine the cause so that you stop the exception from causing the program to terminate prematurely?

(可以使用哪些方法/工具确定原因,以阻止异常导致程序过早终止?)

Sonar with findbugs can detect NPE.

(带有findbug的声纳可以检测NPE。)

Can sonar catch null pointer exceptions caused by JVM Dynamically

(声纳能否动态捕获由JVM引起的空指针异常)


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...