Java 为什么两个不同对象的类Test变量对于==操作为true,而对于字符串对象,相同的操作结果为false?

Java 为什么两个不同对象的类Test变量对于==操作为true,而对于字符串对象,相同的操作结果为false?,java,equals-operator,Java,Equals Operator,For==对使用new创建的两个不同对象s和p的字符串变量的操作将结果设为false(第1行),我理解这一点,但为什么第3行和第4行(注释的行号)将结果设为true作为输出 我知道==是用于引用比较的,这就是我怀疑它是否用于引用比较的原因,那么为什么第4行给出true,因为j是整数,对于字符串(字符串s)没有不变性概念,每次都必须创建一个新对象 class World { public static void main(String[] args) {

For==对使用new创建的两个不同对象s和p的字符串变量的操作将结果设为false(第1行),我理解这一点,但为什么第3行和第4行(注释的行号)将结果设为true作为输出

我知道==是用于引用比较的,这就是我怀疑它是否用于引用比较的原因,那么为什么第4行给出true,因为j是整数,对于字符串(字符串s)没有不变性概念,每次都必须创建一个新对象

    class World
{
    public static void main(String[] args)
    {   
        String s=new String("B");
        String p=new String("B");
        System.out.println(s==p);                    //false    line 1
        Test t1= new Test("A",4);
        Test t2= new Test("A",4);
        System.out.println(t1==t2);                 //false     line 2
        System.out.println(t1.s==t2.s);             //true      line 3
        System.out.println(t1.j==t2.j);             //true      line 4
    }
}

class Test
{
    String s;
    int j;
    Test(String s, int j)
    {
    this.s=s;
    this.j=j;
    }
}

在Java中,对两个整数使用
==
运算符,将它们按值进行比较。同时,对两个字符串或两个类使用
==
比较它们在内存中的位置,而不是它们的值。 在测试类中,您需要小心,因为您将类字段命名为与参数相同的名称,因此您可能不会实际将j和s的值指定给您认为是的值。 尝试将构造函数更改为

Test(String str, int i){
    s = str;
    j = i;
}

字符串通常在java中缓存,因此具有相同值的两个字符串可能具有相同的引用。(整数也是如此,如果某个范围内的对象具有相同的值,它们将被引用为相同的对象)。这可能导致在构造函数中使用与t1和t2的s值相同的对象“A”。如果两个int原语具有相同的值,则它们总是相同的。

“为什么第3行和第4行给出true,因为t1和t2是不同的对象”t1和
t2
是不同的对象,但您不会在第3行中对它们进行比较。您正在比较它们所持有的字符串,这些字符串不是不同的对象。您有两个对同一字符串literal的引用
“A”
,这与您在
s
p
中显式创建新的
string
对象时所做的操作非常不同。您能解释一下这句话吗“整数也是一样,如果某个范围内的对象具有相同的值,那么它们将被引用为相同的对象。”据我所知,只有在Autoboxif中存在两个小整数时才会发生这种情况:Integer i1=Integer.valueOf(127);Integer i2=Integer.valueOf(127);比较将导致i1==i2。如果取而代之的是缓存区域外部的两个整数,即Integer i1=Integer.valueOf(1270);Integer i2=Integer.valueOf(1270);然后比较将导致i1!=i2。您可以通过简单的单元测试轻松验证这一点。或者查看规范:如果自动装箱在内部使用valueOf()方法(如您所述),这是正确的,但在上面的示例中,这两种情况都没有发生。我以整数为例编写了部分(Integers..也是如此),在java中缓存的值可能会导致==运算符的意外结果。正如我在上面的说明中所写的,整数在java中缓存(独立于自动装箱,不受任何契约的valueOf限制)类似字符串。azurefrog的解释是关于比较字符串,字符串可能是相同的对象,而不仅仅是具有相同的值(在这种情况下为“A”).我想说明的是,即使是明显不同的对象,如果它们具有相同的值,也可能拥有相同的引用。由于他将其用于赋值,因此无需更改名称。这与问题无关。