package com.wz.grammer; public class MethondEquals { public static void main(String[] args) { String a = "hello"; String b = "hello"; System.out.println("a.equals(b) : " + a.equals(b)); // true System.out.println("a==b : " + (a==b)); // 注意:算数运算符优先级 > 比较运算符== // true System.out.println("=============="); String c = new String("hello"); String d = new String("hello"); System.out.println("c.equals(a) : " + c.equals(a)); // true System.out.println("c==a : " + (c==a)); // false System.out.println("d.equals(c) : " + d.equals(c)); // true System.out.println("d==c : " + (d==c)); // false } } /* * 字符串创建方式有2种,第1种直接用引号包裹,第2种直接new * 直接引号包裹的方式,字符串存储在字符串常量池中;字符串的引用存储在栈中,引用中保存的是字符串在常量池中的地址。 * 直接引号包裹的方式,不同引用指向的相同字符串,在常量池中只保存了一份。因此不通过引用保存的地址是同一个地址。上述代码打印true可以说明这问题。 * * 直接new的方式,字符串仍然保存在常量池;但是会在堆内存中开辟空间,保存常量池中字符串的地址;栈内存中保存引用,保存堆内存的地址。 * 直接new的方式,本质上是创建新对象,String本质上也是一个类而已。因此即使new的2个字符串对象的字符串内容一致,即使在常量池中对应的都是 * 同一个字符串,由于堆内存中的空间不同,保存在栈中的引用也是不同的。 * * 由于==比较的是应用的地址,因此c==返回false,由于equals比较的是字符串的内容,因此c.equals(a/d)返回的是true。 * * */