一个关于List的基本问题

黑娃 2011-12-09 05:22:58
请看
string ss = new string('2', 4);
ss = "hh";
List<string> ls = new List<string>();
ls.Add(ss);
MessageBox.Show(ls[0]);
ss = "hh2";
MessageBox.Show(ls[0]);
两次show的结果都是hh,证明了容器list里面的实体和外面的ss不是同一个引用

若把string改成控件Butten
Button btn = new Button();
btn.Text = "haha";
List<Button> lsbtn = new List<Button>();
lsbtn.Add(btn);
MessageBox.Show(lsbtn[0].Text.ToString());
btn.Text = "haha2";
MessageBox.Show(lsbtn[0].Text.ToString());
两次show的结果不一样,证明了list里面的实体和外面的btn是一个引用

如果我要装入自己定义的类,情况也同Butten

请问:
List容器什么情况下装入外面对象的引用,什么时候装入外面对象的副本
我一直以为c#里面凡是要new才能用的对象,都像是C++里面的智能指针,但string却不是这样,能仔细说明下吗?
...全文
335 13 打赏 收藏 转发到动态 举报
写回复
用AI写文章
13 条回复
切换为时间正序
请发表友善的回复…
发表回复
hztltgg 2011-12-09
  • 打赏
  • 举报
回复
string就是一个特殊的引用类型,使用上却和值类型更相似。
阿非 2011-12-09
  • 打赏
  • 举报
回复
你这个问题和List<string> 没关系。

只是你不了解 string 的特性而已。 说string是值类型的先看看MSDN,这是最基础的了。

你需要先了解一下 string 的 immutable
zh6335901 2011-12-09
  • 打赏
  • 举报
回复
[Quote=引用 5 楼 dalmeeme 的回复:]

很简单,
c#中string对象是不可变,对string对象的赋值或操作都只是重新创建一个string对象。
[/Quote]
+1,如果你使用字符串驻留技术的话,你就会发现2次show的结果是不一样的了
zaytsing 2011-12-09
  • 打赏
  • 举报
回复
我这么你可能还不是很清楚,告诉你一个测试的方法。。到底是不是同一个对象,你用Equal和==判断一下,把
ls[0]和ss对比下,然后在lsbtn[0].Text和btn.Text对比,打出4个结果,再设断点追踪。我也有点脑袋晕了,我找个c++大牛辩论一下,有点混淆了。。
zaytsing 2011-12-09
  • 打赏
  • 举报
回复
这个你要充分去了解值类型和引用类型。。string s=new string(“”),它还是值类型,跟string s=“”是一个意思的;它只在堆上分配内存,你也去了解堆栈。相当容易理解。值类型就那么几种。堆是由计算机分配,栈是由程序员自己分配,C#里不用你手工释放,由它自己的回收机制完成,C++你一定要手工释放。C#里你不要看他没指针和引用概念,其实随时都存在。。你new一个对象就是一个引用,集合或数组按索引取数据用的就是引用,枚举也是引用。引用C++就是指针,当然只是写法不同,c++带*表示指针,而C#直接把整个指针都封装,不用管它,直接数据类型对上就可以放进去用。还要告诉你的是,虽然C#没指针概念,但是指针应用还是很广的,c++里面的指针在c#里通常都是值指针,就是指向对象或数据,c#的委托也是一种指针应用,它还可以指向一个方法。这是c#里说的引用指针。
Sundays 2011-12-09
  • 打赏
  • 举报
回复
[Quote=引用 5 楼 dalmeeme 的回复:]
很简单,
c#中string对象是不可变,对string对象的赋值或操作都只是重新创建一个string对象。
[/Quote]
同意
火雲邪神 2011-12-09
  • 打赏
  • 举报
回复
good post ar
tanghuawei 2011-12-09
  • 打赏
  • 举报
回复
看看这个:http://www.cnblogs.com/tling091223/archive/2009/12/23/1630338.html
dalmeeme 2011-12-09
  • 打赏
  • 举报
回复
很简单,
c#中string对象是不可变,对string对象的赋值或操作都只是重新创建一个string对象。
jiuhexuan 2011-12-09
  • 打赏
  • 举报
回复
我理解的有问题,看2楼吧
jiuhexuan 2011-12-09
  • 打赏
  • 举报
回复
引用对象,声明后
堆栈上
其实是,变量名+指针,指针指到堆上的对象
堆栈上
值类型,是变量名+值

你修改引用对象,其实是修改,堆上的内容,任何地方修改变量,都是如此。
修改值类型,就直接修改堆栈上的值

但string类型是不可修改的,或者说,修改的时候,直接在堆栈上又分配了空间。
你之前的使用,是直接把内容放到了应用对象内部的。

可以认为string是值类型
kingdom_0 2011-12-09
  • 打赏
  • 举报
回复
c02645 2011-12-09
  • 打赏
  • 举报
回复
string,int...是特殊的引用类型,它的实例是只读的
List<String>为何不能赋值给List 今天有个同事让我实现一个接口,这个接口里的一个方法类似于:set(List param),也即参数类型是List 我有几个方法要调用这个接口,实参类型都类似于:ListList。结果调用发现报错,参数类型不匹配。 纳闷了...
可以把List<String>传递给一个接受List参数的方法吗? 可以把List传递给一个接受List参数的方法吗?  [复制链接] jiangweibin2573 该用户从未签到 13 黑马币 25 技术分 11 主题 中级黑马 发消息 电梯直达 楼主

110,539

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧