Java question about autoboxing and object equality / identity [duplicate]

ε祈祈猫儿з 提交于 2019-11-28 07:34:51

Read this.

Java uses a pool for Integers in the range from -128 to 127.

That means if you create an Integer with Integer i = 42; and its value is between -128 and 128, no new object is created but the corresponding one from the pool is returned. That is why c1 is indeed identical to c2.

(I assume you know that == compares references, not values, when applied to objects).

The correct answers have already been given. But just to add my two cents:

Integer b1 = 1000, b2 = 1000;

This is awful code. Objects should be initialized as Objects through constructors or factory methods. E.g.

 // let java decide if a new object must be created or one is taken from the pool
Integer b1 = Integer.valueOf(1000);

or

 // always use a new object
 Integer b2 = new Integer(1000);

This code

Integer b1 = 1000, b2 = 1000;

on the other hand implies that Integer was a primitive, which it is not. Actually what you are seeing is a shortcut for

Integer b1 = Integer.valueOf(1000), b2 = Integer.valueOf(1000);

and Integer only pools objects from -127 to 127, so it will create two new Objects in this case. So although 1000 = 1000, b1 != b2. This is the main reason why I hate auto-boxing.

Because Integer is for a few low numbers like enumeration so there is always same instance. But higher numbers creates new instances of Integer and operator == compares their references

Zoltan Balazs

You can find the answer here:

Strangest language feature in the 6th answer.

Edit: sorry not exatly the answer. The point is that == compares references, not values when you use it with Integer. But with int "==" means equals.

  public static Integer valueOf(int i) {
      final int offset = 128;
      if (i >= -128 && i <= 127) { // must cache
          return IntegerCache.cache[i + offset];
      }
       return new Integer(i);
    }

Because of this you true in one case, and false in other!

The answer you want is here

If autounboxing had worked also when doing equality checking with the '==' operator you could write:

    Long notNullSafeLong1 = new Long(11L)
    Long notNullSafeLong2 = new Long(22L)
    if ( notNullSafeLong1 == notNullSafeLong2) {
      do suff

This would require implementing an override for == so that null==someLong is false and the special case Null==Null is true. Instead we have to use equal() and test for null

    Long notNullSafeLong1 = new Long(11L)
    Long notNullSafeLong2 = new Long(22L)
    if ( (notNullSafeLong1 == null && notNullSafeLong2 == null) || 
      (notNullSafeLong1 != null && notNullSafeLong2 != null & 
        notNullSafeLong1.equals(notNullSafeLong2)) {
      do suff    

This is alittle more verbose than the first example - if autounboxing had worked for the '==' operator.

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!