简体   繁体   中英

“JOptionPane java.lang.NullPointerException” error in Java

This is my full code:

import javax.swing.JOptionPane;

public class Lab5bug {

public static void main(String[] args) {

    int x=0;
    String str;
    for (;;)
    {
        str = JOptionPane.showInputDialog("Enter a grade 0-100\n(Hit Cancel to abort)");
        if (str==null || str.equals(""))
            break;
        x = Integer.parseInt(str);
        if (x>=0 && x<=100)
            break;
        JOptionPane.showMessageDialog( null, "Invalid grade, try again");
    }
    if (str != null  & !str.equals(""))   //<===========BUG:  NEEED TO USE && 
        //&,||.| are all lead to bug if we press Cancel.
        //str can be null it does not pass 1st condition
        //but still pass 2nd condition
        //str can be "" pass first condition but not second condition
        //and therefre it still show the message The grade is 0
        //But why 
        JOptionPane.showMessageDialog( null, "The grade is " + x);
}
}

When I run the program and press Cancel at the first dialog box, then the program returns a error:

Exception in thread "main" java.lang.NullPointerException
at Lab5bug.main(Lab5bug.java:19)

I have already located the problem, at this line if (str != null & !str.equals("")) But why only && works? I do not understand the logic behind this.

& does not short circuit the statement, meaning that if str != null is false, it still tries str.equals("") which would cause a NPE if str is null. The system naively evaluates the second part of the statement with & even if the first part is false.

&& works because it short circuits the statement, and if str != null is false, it breaks from the statement not evaluating the second part of the statement and avoiding the NPE; because the statement can't be true if the first value is false.

Most of the time && is more desirable than & .

Also the same rule applies to OR, | and || . true | throw new RuntimeException("Second part of statement was evaluated "); will throw that exception, whereas true || throw new RuntimeException("Second part of the statement was evaluated") true || throw new RuntimeException("Second part of the statement was evaluated") will not reach the exception because the statement is guaranteed to be true because the first part of the statement evaluates to true, so it short circuits and breaks from the statement.

Replace

if (str != null & !str.equals(""))

with

if (str != null && !str.equals(""))

& stands for bitwise AND. Therefore when str is null, the expression !str.equals("") throws a NullPointerException . When the logical AND operator && is used, the !str.equals("") expression won't be reached because the first condition str != null is false.

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