简体   繁体   中英

Why does the Java compiler sometimes allow the unboxing of null?

For example:

int anInt = null;

fails at compile time but

public static void main(String[] args) {
  for (int i = 0; i < 10; i++) {
    System.out.println("" + getSomeVal());
  }
}
public static int getSomeVal() {
   return new Random().nextBoolean() ? 1 : null;
}

fails (usually) at run time. Trying to return just null will also result in a compile error, so I assume there is something about having multiple paths that causes the compiler to infer that null is potentially an autoboxed int ? Why can javac not fail to compile both cases with the same error?

In the first case, the compiler knows that you're trying to unbox a compile-time constant of null .

In the second case, the type of the conditional expression is Integer , so you're effectively writing:

Integer tmp = new Random().nextBoolean() ? 1 : null;
return (int) tmp;

... so the unboxing isn't happening on a constant expression, and the compiler will allow it.

If you changed it to force the conditional expression to be of type int by unboxing there , it would fail:

// Compile-time failure
return new Random().nextBoolean() ? 1 : (int) null;

Boxing partially hides the distinction between primitives and corresponding wrapper objects, but it doesn't remove it.

There are two distinctions which are not changed by boxing:

  • objects can be null, while primitives cannot
  • objects have both state and identity, while primitives have only state (the value)

Occasionally, these differences can cause problems when using boxing.

Some points to remember :

  • be careful with nulls. Auto-unboxing a null object will cause a NullPointerException .
  • comparing items with == and equals must be done with care.

You can't assign null to an int

    int anInt = null;

Java allows this since you are not assigning null to an int

    System.out.println("" + getSomeVal()); //null was just converted to a srting and was printed

If you perform this, you can get the error

    int anInt = getSomeVal();

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