进来看看,你也会很疑惑的。

guodong66 2009-10-28 09:48:39
class Test2 {
String a = "1";
String b = "2";
}
public class NoUpdate {
public static void changeUpd(Test2 t) {
t.a = "abc";
t.b = "123";
}
public static void main(String[] args) {
Test2 t2 = new Test2();
changeUpd(t2);
System.out.println(t2.a + "----" + t2.b);
}
}

这个程序输出 abc----123 ;
但是如果修改一下,
publicclass Test1 {

publicstaticvoid changeStr(String str){
str="welcome";
}
public static void main(String[] args) {

String str="1234";
changeStr(str);
System.out.println(str);
}
}
这里就输出 1234
同样传递的是对象,为什么第二个程序的值没有被修改呢?两个程序传递的参数都应该是原对象的引用的,为什么?想不明白,呵呵
...全文
135 点赞 收藏 24
写回复
24 条回复
切换为时间正序
当前发帖距今超过3年,不再开放新的回复
发表回复
sangshusen_1988 2009-10-28
值传递和引用传递
回复
guodong66 2009-10-28
楼上的你没看懂我的意思么? 两次传入的都是对象类型,传入String时,虽然String被修改了,但是打印的还是原来的String ,当传入其他类型对象时,被修改后就打印出被修改后的对象的值。
回复
x-teamer团队 2009-10-28
String类是什么呢!final的

第二例子中



publicstaticvoid changeStr(String str){
str="welcome";
}



相当于:



publicstaticvoid changeStr(String str){
str= new String("welcome");
}



所以,传参都是引用值的复制, 任何引用传递进来之后,如果重新分配一个new 对象,

都仅仅发生在复制过来的引用参数上,对原来对象不会产生任何作用,除非是这样的:



publicstaticvoid changeStr(MyClass a){
a.attribute = "12123";//注意不是new哦!
}



我之前做了一个比较完善的总结,希望对你有帮助:

http://blog.csdn.net/ostrichmyself/archive/2009/10/03/4630976.aspx

回复
py330316117 2009-10-28
class Test2 {
String a = "1";
String b = "2";
}
public class NoUpdate {
public static void changeUpd(Test2 t) {
t.a = "abc";
t.b = "123";
}
public static void main(String[] args) {
Test2 t2 = new Test2(); //a=“1”,b=“2”
changeUpd(t2); //a="abc",b="123"
System.out.println(t2.a + "----" + t2.b); //打印
}
}
这个程序输出 abc----123 ;
但是如果修改一下,
public class Test1 {

public static void changeStr(String str){
str="welcome";
}
public static void main(String[] args) {

String str="1234"; //主函数中的str=“1234”
changeStr(str); changeStr中的“welcom”被改为“1234”,但是主函数中的值没被改变
System.out.println(str); //输出主函数中的值是“1234”
}
}
这里就输出 1234
lz说的“两个程序传递的参数都应该是原对象的引用的”,你引用的没错,不过传值并不是一样的
回复
guodong66 2009-10-28
final class Test2 {
String a = "1";
String b = "2";
}

public class NoUpdate {
public static void changeUpd(Test2 t) {
t.a = "abc";
t.b = "123";
}

public static void main(String[] args) {
Test2 t2 = new Test2();
changeUpd(t2);
System.out.println(t2.a + "----" + t2.b);
}
}

楼上你在试试这个,并不是final的原因。
回复
xiandulina 2009-10-28
[Quote=引用 7 楼 onlylikejava 的回复:]
因为String对象的值一旦创建是不可改变的。String类是个final类。
[/Quote]

	public static void main(String[] args) {
String a = "a";
a = "b";
System.out.println(a);
}

你说a是多少
回复
guodong66 2009-10-28
网卡,貌似发重复了。。。
回复
OnlyLikeJava 2009-10-28
因为String对象的值一旦创建是不可改变的。String类是个final类。
回复
xierangh 2009-10-28
class Test2 {
String a = "1";
String b = "2";
}
public class NoUpdate {
public static void changeUpd(Test2 t) {
t.a = "abc";
t.b = "123";
}
public static void main(String[] args) {
Test2 t2 = new Test2();
changeUpd(t2);
System.out.println(t2.a + "----" + t2.b);
}
}

这里在内存堆里的对象是t2,你改变的是对象里的内容。


publicclass Test1 {

publicstaticvoid changeStr(String str){
str="welcome";
}
public static void main(String[] args) {

String str="1234";
changeStr(str);
System.out.println(str);
}
}

这里的对象是str,你修改的也是str。
回复
heroboy0923 2009-10-28
lz可以试试把代码中的String换成StringBuffer或者StringBuilder,就会发现结果输出的是welcome,因为StringBuffer是可以改变所引用的内用的,而不是重新分配内存
因此我们编程的时候,如果需要频繁的改变字符串内容,应该考虑使用StringBuffer或者StringBuilder(两者的区别在于前者是线程安全的,对于一个线程的情况,用StringBuilder效率更高),以节省内存空间,
回复
heroboy0923 2009-10-28
java传参的时候,基本数据类型是按值传递,对象类型是按引用传递
String是对象,应该是按引用传递,但是String是一种特殊的对象,即他所引用的值是无法改变的
一开始的时候main方法中的str所引用的对象是"1234",当执行到changeStr(str)时,会把changeStr中的str指向"1234",这时候内存中有两个str,所引用的内容都是"1234",在往下,让changeStr中的str引用"welcome",注意这里要提到String对象的一个特性,即他的内容是无法改变的,起初str = "1234",当str = “welcome”时,并没有将1234换成welcome,而是重新分配一个内存存储"weilcome",然后让str引用该内容,而main中的str依然引用的是"1234"
回复
melody1616 2009-10-28
public static void changeStr(String str){
str="welcome";
}
可以试试不要void,让它return str;
回复
potahai 2009-10-28
[Quote=引用楼主 guodong66 的回复:]
class Test2 {
String a = "1";
String b = "2";
}
public class NoUpdate {
public static void changeUpd(Test2 t) {
t.a = "abc";
t.b = "123";
}
public static void main(String[] args) {
Test2 t2 = new Test2();
changeUpd(t2);
System.out.println(t2.a + "----" + t2.b);//这里你引用的是一个对象T2
}
}

这个程序输出 abc----123 ;
但是如果修改一下,
publicclass Test1 {

publicstaticvoid changeStr(String str){
str="welcome";
}
public static void main(String[] args) {

String str="1234";
changeStr(str);
System.out.println(str);//这里输出的只是在MAIN方法里NEW的STRING 上面的STR只是适用于方法内。并没有在类中分配一个静态内存 使用完就释放掉了。
}
}
这里就输出 1234
同样传递的是对象,为什么第二个程序的值没有被修改呢?两个程序传递的参数都应该是原对象的引用的,为什么?想不明白,呵呵
[/Quote]
回复
JavaAlpha 2009-10-28
建议你加个断点,再一步步跟进去看看。具体的值的变化会一目了然。
回复
zhuzeitou 2009-10-28
额,上面的……是说继承……
回复
zhuzeitou 2009-10-28
你这个final有意义么?你又不去……
人家final指的是private final char value[]; 这句好不好
回复
guodong66 2009-10-28
[Quote=引用 19 楼 heroboy0923 的回复:]
public final class String
    implements java.io.Serializable, Comparable <String>, CharSequence
{
    /** The value is used for character storage. */
    private final char value[];

    /** The offset is the first index of the storage that is used. */
    private final int offset;

    /** The count is the number of characters in the String. */
    private final int count;

    /** Cache the hash code for the string */
    private int hash; // Default to 0
*************************************************
上面是用jad反编译之后得到的源代码,可以看到String其实就是final char value[],因为是final的,所以他的值一旦被确定之后就无法改变,而你写的那个例子如果String a和String b都声明为final,你的代码就错了……
[/Quote]

服了,这和final没关系,我知道String是final类型的,你仔细看了我10楼的例子在说。我晕啊。
final class Test2 {
String a = "1";
String b = "2";
}
这里已经声明为final了。
回复
zhuzeitou 2009-10-28
想到的例子已存在与18楼………………
回复
feng_jyie 2009-10-28
楼主赶快结贴吧
回复
heroboy0923 2009-10-28
public final class String
implements java.io.Serializable, Comparable<String>, CharSequence
{
/** The value is used for character storage. */
private final char value[];

/** The offset is the first index of the storage that is used. */
private final int offset;

/** The count is the number of characters in the String. */
private final int count;

/** Cache the hash code for the string */
private int hash; // Default to 0
*************************************************
上面是用jad反编译之后得到的源代码,可以看到String其实就是final char value[],因为是final的,所以他的值一旦被确定之后就无法改变,而你写的那个例子如果String a和String b都声明为final,你的代码就错了……
回复
发动态
发帖子
Java SE
创建于2007-09-28

6.1w+

社区成员

Java 2 Standard Edition
申请成为版主
社区公告
暂无公告