[菜鸟原创] 值类型-引用类型-string

大狗狗 2008-11-20 10:08:05
本人系C#初学者,贴上个人学习所思,与大家共享。欢迎批抨指正!

作者:win32fan(QQ184263203)

值类型与引用类型的本质区别是什么?

值类型是基本的数据类型,包括简单数据类型如int 、char等,或是由它们组合起来的结构。

引用类型在数据结构上包含值类型及其它引用类型。但引用类型的本质不是用来描述数据,而是用来描述操作数据的方法。我认为这才是值类型和引用类型的本质所在:

值类型用来描述数据,引用类型用来描述操作数据的方法。

有了这个理论前题,就不难理解:
int i=8;
int j=i;
i和j表示不同的两个数据.

class A;
A a=new A();
A b=a;
a和b所指同一个"方法"

怪物: string

C#声明string是引用类型,但有菜鸟却不能理解下面代码:
class Program
{
static void StringCon(string str)
{
str="New String";
}

public static void Main(string[] args)
{
Console.WriteLine("Hello World!");

// TODO: Implement Functionality Here
string oldstr ="str";
Console.WriteLine("before:{0}",oldstr );
StringCon(oldstr );
Console.WriteLine("after:{0}",oldstr );
Console.Write("Press any key to continue . . . ");
Console.ReadKey(true);
}
}

输出:before:str
after:str

也就是"没有引用类型的应该有的表现"。这是为什么了?

其实,这是菜鸟对程序阅读理解有误(当然也和string的特殊性有关)。引用类型本应都使用new操作符来创建新的实例。但考虑到 string类型 的使用较频繁,为了简化代码书写,C#特许string使用"="来创建实例。因此:

str="New String";
其实是:str=new string("New String");
菜鸟们看到了"="号,误将其当作值类型的赋值操作符,其实这个"="是用来创建新实例的。

最后,为什么C#要将string划作引用类型呢?我想这是因为string具有length属性、具有CopyTo、InDexOf等一系列需要用到的方法。虽然它具有值类型一些特点,但根据前面所讲值类型及引用类型本质区别,C#还是将其放入了引用类型中。与之相反的是结构,结构也可以包含方法,但本质上结构主要是用来描述数据的,因而被放到了值类型中。




...全文
109 13 打赏 收藏 转发到动态 举报
写回复
用AI写文章
13 条回复
切换为时间正序
请发表友善的回复…
发表回复
li_E_KID_ 2011-10-05
  • 打赏
  • 举报
回复
up!!!!!!!
wangping_li 2008-11-20
  • 打赏
  • 举报
回复
:)
wangkk125 2008-11-20
  • 打赏
  • 举报
回复
上面错了,应该这样
值类型存放在堆栈中
引用类型放在堆中
值的大小是固定的,而引用类型的空间是不可预算的
因此它指向的是一个地址
wangkk125 2008-11-20
  • 打赏
  • 举报
回复
值类型存放在堆中
引用类型放在堆栈中
值的大小是固定的,而引用类型的空间是不可预算的
因此它指向的是一个地址
大狗狗 2008-11-20
  • 打赏
  • 举报
回复
再贴段代码:(老贴里的)关键地方加上我注释

下面两段代码,为什么它们的输出结果不同?string也是引用类型,为什么看起来像值类型?
//use string
…………
public static int Main()
{
string str1,str2;
str1="abc";
str2=str1; // 刚开始str2的内容和str1相同,两者共享同一实例 Console.WriteLine("First,str1={0}, str2={1}",str1,str2);
str2="def"; //注意,这里是创建新实例,str2将指向新实例 Console.WriteLine("Again,str1={0}, str2={1}",str1,str2);
return(0);
}
…………
输出:
First,str1=abc, str2=abc
Again,str1=abc, str2=def

//use ecumenic class
class class2
{
public string s;
}

class Class1
{
public static int Main()
{
class2 str1,str2;
str1=new class2();

/*前面的str1和str2(类型是string)虽然开始指向同一实例,但后面就"各有所指"了。注意:这里的str1和str2却始终指向同一实例(类型是class2)!因此str2.s="def";就等于同时执行了str1.s="def";*/ str2=str1;
str1.s="abc"; // 这是对类成员操作 Console.WriteLine("First,str1={0}, str2={1}",str1.s,str2.s);
str2.s="def"; // 这是对类成员操作
Console.WriteLine("Again,str1={0}, str2={1}",str1.s,str2.s);
return(0);
}
}
输出:
First,str1=abc, str2=abc
Again,str1=def, str2=def
whitechololate 2008-11-20
  • 打赏
  • 举报
回复
mark
分配空间不同,堆,栈的区别
引用类型 传递引用,类似c++指针,指向存储地址
claymore1114 2008-11-20
  • 打赏
  • 举报
回复
顶!up
BernardSun 2008-11-20
  • 打赏
  • 举报
回复
slin60 2008-11-20
  • 打赏
  • 举报
回复
每个人的理解方式不同,只要知道怎么用就行了
我姓区不姓区 2008-11-20
  • 打赏
  • 举报
回复
[Quote=引用楼主 Win32FanEx 的帖子:]
最后,为什么C#要将string划作引用类型呢?
[/Quote]
因为它相当于一个char数组,数组是属于引用类型的
C_sdnElf 2008-11-20
  • 打赏
  • 举报
回复
顶下!
绝代坏坏 2008-11-20
  • 打赏
  • 举报
回复
:)
没有梦想 2008-11-20
  • 打赏
  • 举报
回复
比较透彻,本人不钻牛角尖。

111,130

社区成员

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

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

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