这有几个和String有关的问题,请大家帮忙分析
1.
public class Test
{
public static void main(String args[])
{
String s="abc";
s=s.contact("def");
System.out.println(s);
}
}执行结果为abcdef 书上不是说String的实例对象一旦创建,则它所包含的字符序列不发生变化吗?现在怎么变化了
2
public class J_String
{
public static void operate(String x,String y)
{
x.contact(y);
y=x; }
public static void main(String args[])
{
String a="a";
String b="b";
operate(a,b);
System.out.println(a+"."+b);
}}
执行结果为a.b,为什么operate中的y=x没有作用呢,x.contact(y),也没作用呢?
3.
public class J_StringArray
{
public static void swap(String s[])
{
if(s.length<2)
return;
String t=s[0];
s[0]=s[1];
s[1]=t;
}
public static void main(String args[])
{
String s[]={"1","2"};
swap(s);
System.out.println(s[0]+s[1]);
}
}
执行结果为21,为什么它们没有交换呢?
请大家针对这几个问题,给我讲讲这里面的门道,小弟在这谢谢大家了。
1.
public class Test
{
public static void main(String args[])
{
String s="abc";
s=s.contact("def");
System.out.println(s);
}
}执行结果为abcdef 书上不是说String的实例对象一旦创建,则它所包含的字符序列不发生变化吗?现在怎么变化了
2
public class J_String
{
public static void operate(String x,String y)
{
x.contact(y);
y=x; }
public static void main(String args[])
{
String a="a";
String b="b";
operate(a,b);
System.out.println(a+"."+b);
}}
执行结果为a.b,为什么operate中的y=x没有作用呢,x.contact(y),也没作用呢?
3.
public class J_StringArray
{
public static void swap(String s[])
{
if(s.length<2)
return;
String t=s[0];
s[0]=s[1];
s[1]=t;
}
public static void main(String args[])
{
String s[]={"1","2"};
swap(s);
System.out.println(s[0]+s[1]);
}
}
执行结果为21,为什么它们没有交换呢?
请大家针对这几个问题,给我讲讲这里面的门道,小弟在这谢谢大家了。
2.java是值传递,而且String是final的,不可变的
3.是交换了,字符串数组可以理解为对一个特殊的对象,里面的属性字段都是字符串,属性改变了,那整个对象肯定变了,就像下面public class StringObject
{
String str; public static void main(String[] args)
{
StringObject so = new StringObject();
so.str = "abc";
System.out.println(so.str);
so.str = "def";
System.out.println(so.str);
so.union("ghi");
System.out.println(so.str);
}
public void union(String s)
{
str +=s;
}
}
y=x;此处也是起作用的,你在这句下面加个打印就知道了。
但回到main方法中:
String a="a"; //一个对象
String b="b"; //一个对象
按理说是一个引用的交换,但这里没有将a="b",到是与值类型相似了,这里我还真没有研究过,待高人指点。3、结果不是已经交换了么?开始是 1,2,后面是2,1。难道我看错题了?
int otherLen = str.length();
if (otherLen == 0) {
return this;//传入0长度的字符串返回自身
}
char buf[] = new char[count + otherLen];
getChars(0, count, buf, 0);
str.getChars(0, otherLen, buf, count);
return new String(0, count + otherLen, buf);//返回新的字符串了
}
楼主要搞清楚引用(句柄)跟对象的区别,借用编程思想的比喻:引用相当于“遥控器”,对象相当于“电视机”,你可以通过引用来控制对象,但是引用改变了,不影响对象。这里是把引用改变了但是原来的String对象没有变化,只是你不能通过s这个引用来访问它了。
第二三个问题就是java方法调用传值的特点:把引用传递给方法以后,方法内部会重新生成跟传入引用的副本,就相当于方法内部“克隆”出来个传入一样的引用,它俩指到同一个对象上面,所以可以通过“克隆”出来的引用来改变原对象的内容问题三,但是对于问题二你是把“克隆”出来的引用重新指向了,但是不会影响原来的引用。
String是属于对象,对象是引用,是将对象的地址传过去,而不是将值过去了。
你理解为传值也可以,不过记住普通的是传值,引用的是传地址
2.java是值传递的,你在operator里y=x,只改变的是operator方法里y的值,main方法里b还是指向“b”的
3.交换了啊,你可以执行交换方法前也打印下
都没权限改自己回复下面补充下
String的确是final的,一旦创建就不能改变,s.contact("def");执行这句后,“abc”还在String池中,而且创建了一个新的String" abcdef" 然后你通过赋值操作将s变量重新引用到了"abcdef",而不再指向原来的"abc"了,你可以试下不进行赋值操作,s的值就不会变了。
{
public static void operate(String x,String y)
{
x = x.contact(y);
y=x;
System.out.println(x+"."+y); }
public static void main(String args[])
{
String a="a";
String b="b";
operate(a,b);
System.out.println(a+"."+b);
}}
3. 3和2基本是一个问题,在swap(String s[])方法中的操作不影响main方法中的String类的值。
1. String s1=new String("a");//相当于new出一个对象s持有对它的引用
String s2=new String("a");//又在堆内存new出一个对象,
System.out.println(s==s);//输出false,==比较的是堆内存中2个对象的地址值
----------------------------------------------------------------------------------
2. String s1="a";//new一个对象放到池里面
String s2="a";//从池中寻找"a"对象赋给s2
所有此时s2持有该对象的引用。
System.out.println(s1==s2);//输出true
public String concat(String s)
{
int i = s.length();
if(i == 0)
{
return this;
} else
{
char ac[] = new char[count + i];//构建字符序列
getChars(0, count, ac, 0);//复制原来的字符序列
s.getChars(0, i, ac, count);//添加新的字符序列
return new String(0, count + i, ac);//用构建好的字符新序列创建一个String对象并返回
}
}
所以每次调用String对象的concat方法必须获取方法返回的新对象。