以下Java代码中使用的表达式是非常不可接受的,尽管我仅仅为了一般目的而测试它们并获得了一些意想不到的结果。简单的代码片段如下。
package wrapper;
final public class Main
{
public static void main(String[] args)
{
Integer j1 = 127;
Integer j2 = 127;
System.out.println(j1==j2); //returns true!!!
Integer k1 = 128;
Integer k2 = 128;
System.out.println(k1==k2); //returns false!!!
Integer w1 = -128;
Integer w2 = -128;
System.out.println(w1==w2); //returns true!!!
Integer m1 = -129;
Integer m2 = -129;
System.out.println(m1==m2); //returns false!!!
}
}
Integer j1 = 127;
Integer j2 = 127;
System.out.println(j1==j2);
上面的代码显然显示 true 因此,毫无疑问。
Integer k1 = 128;
Integer k2 = 128;
System.out.println(k1==k2);
上述代码预计在控制台上显示为true,但令人惊讶的是,它显示 false 。为什么呢?
Integer w1 = -128;
Integer w2 = -128;
System.out.println(w1==w2);
此代码显示 true ,对此毫无疑问。
Integer m1 = -129;
Integer m2 = -129;
System.out.println(m1==m2);
上面的代码再次显示 false ,但预计会返回true。为什么呢?
答案 0 :(得分:9)
Integer
被缓存,因此j1
和j2
来自:
Integer j1 = 127;
Integer j2 = 127;
指向同一个对象。
当然,这是一个JVM实现的东西,所以你永远不应该假设它们被缓存了。要比较参考类型,请不要使用==
,而是使用他们的equals(...)
方法。
答案 1 :(得分:4)
请注意
之间存在差异int k1 = 128;
int k2 = 128;
System.out.println(k1==k2);
和
Integer k1 = 128;
Integer k2 = 128;
System.out.println(k1==k2);
第一个是创建简单的数字类型。第二个是创建对象类型,它包含数值类型以允许它们传递给期望对象的函数。
在第一种情况下,简单数字类型只有一个值,并且在使用==时进行比较。但是,创建的对象不使用==来比较它们的值。相反,他们使用==来说明它们是否是同一个对象,并使用.equals()
方法来说明它们是否具有相同的值。 Java中没有运算符重载,因此任何时候将对象与==进行比较,它总是会问“这是同一个对象吗?”而不是“这两个对象具有相同的价值吗?”
因此,在这种情况下,您提供的代码相当于
Integer k1 = new Integer(128);
Integer k2 = new Integer(128);
System.out.println(k1==k2);
返回false,因为k1和k2不是同一个对象。相反,如果你这样做:
Integer k1 = 128;
Integer k2 = k1;
System.out.println(k1==k2);
你会成真。
实际上,令人惊讶的部分是您上述测试的任何结果都是正确的。这是因为Java为小数字(-128到127,即一个字节大小)保留了一组整数,并在可能时将它们用于分配。
答案 2 :(得分:3)
==运算符检查引用相等性,在上面的代码中不能保证为真。
要比较值是否相等,请使用m1.equals(m2)
。
答案 3 :(得分:1)
这是因为java的整数缓存,因为你使用的是==运算符而不是equals()。
使用==表示比较对象的引用。
整数A = 135; 整数B = 135;
A == B将评估他们的引用是否相同(它们是否是同一个对象),而不是它们是否相等。
此外,如果A和B在(-128,127)之间,它们被缓存 - 意味着如果A和B是35,它们实际上将是相同(缓存)的对象,这就是为什么你得到A == B如果yhey在上面的范围内。
在这种情况下使用equals。
答案 4 :(得分:1)
因为将对象与==
运算符进行比较是不正确的,该运算符比较非基本类型的对象引用。 ==
运算符可以比较原始类型。必须使用equals
方法比较引用类型(Integer,Float,Double和其他对象)。
有时==
可能对Integer这样的类型起作用的原因是内部缓存。当你声明这样的整数时:
Integer i = 10;
相当于:
Integer i = Integer.valueOf(10);
对于-128到127之间的值,该值是从缓存中获取的,这意味着后续调用将返回相同的对象。
但如果你试试这个:
Integer i1 = new Integer(10);
Integer i2 = new Integer(10);
System.out.println(i1 == i2); // prints false
您将有两个不同的对象,它们的引用不相等。要获得正确的结果,您应该按如下方式对它们进行比较:
Integer i1 = new Integer(10);
Integer i2 = new Integer(10);
System.out.println(i1.equals(i2)); // prints true
您应该阅读equals
和hashCode
方法以及它们之间的合同