测试1:
代码
public class Test { public static void main(String[] args) { String s1="aaa"; f(s1); System.out.println(s1); } public static void f(String s2){ System.out.println(s2); s2="bbb"; } }
输出结果
aaa aaa
可以看到 方法f 对字符串的修改是没有意义的;
测试2:
先创建一个实体对象p 设置String 熟悉 n
public class P { private String n; public String getN() { return n; } public void setN(String n) { this.n = n; } }
测试类对元测试类进修改:
public class Test { public static void main(String[] args) { String s1="aaa"; // f(s1); // System.out.println(s1); P p1 = new P(); p1.setN(s1); f(p1); System.out.println(p1.getN()); } public static void f(String s2){ System.out.println(s2); s2="bbb"; } public static void f(P p2){ System.out.println(p2.getN()); p2.setN("bbb"); } }
输出
aaa bbb
可以看到字符串在测试2中改变了,这是什么原因呢。
首先我们看一下String的特点,入下图从java代码中可以看到String是一个常量是不可改变的,所以每次对String进行修改时起始是创建了一个新的对象。
测试1JVM分析:s1和s2其实都是对字符串“aaa”的引用,s1和s2 都指向内存“aaa” ,当执行 s2="bbb" 时 s2 的地址指向“bbb” ,s1仍然指向“aaa”。
测试2 JVM分析:p1和p2 都是对象P的引用,执行 p2.setN("bbb"); 时对象P 的属性 n 地址从“aaa” 指向到"bbb" ,
所以执行 System.out.println(p1.getN()); 打印出"bbb"。