char + char = int? 为什么?
为什么将C#结果中的两个char
添加到int
types?
例如,当我这样做:
var pr = 'R' + 'G' + 'B' + 'Y' + 'P';
pr
variables变成一个int
types。 我期望它是一个值为"RGBYP"
的string
types。
为什么C#是这样devise的? 是不是添加两个char
的默认实现应该是一个string
连接char
,而不是int
?
根据char的文档,可以隐式转换为整数值。 char
types没有定义自定义operator +
所以使用整数。
在Eric Lippert的博客文章“为什么字符会隐式转换为ushort,而不是反之亦然”中的第一条评论中解释了没有对string隐式转换的基本原理。 :
它在v1.0被考虑。 1999年6月6日的语言devise笔记说:“我们讨论了这种转换是否应该存在,并决定提供第三种转换方法是很奇怪的[语言]已经支持c.ToString()和new串(C)”。
( 发信给JimmiTh 查找该报价 )
char
是一个值types,意味着它有一个数值(它的UTF-16 Unicode序数)。 但是,它不被认为是一个数字types(如int,float等),因此,没有为char定义+运算符。
但是, char
types可以隐式转换为数字型的int
types。 由于它是隐含的,因此编译器可以根据C#规范中规定的一组优先规则为您进行转换。 int
是通常尝试的第一件事情之一。 这使得+
运算符有效,所以这就是所执行的操作。
要做你想做的事,从一个空string开始:
var pr = "" + 'R' + 'G' + 'B' + 'Y' + 'P';
与chartypes不同,stringtypes为Object定义了一个重载的+运算符,它将第二项(不pipe它是什么)转换为使用ToString()
的string,然后将它连接到第一项。 这意味着不执行隐式转换; 现在你的pr
variables被推断为一个string,并且是所有字符值的连接。
因为单个字符可以转换为Unicode值,并且可以很容易地存储为占用比单个字符string更less的空间的整数。
从MSDN :
Char对象的值是一个16位数字(有序)值。
char是一个整数types。 这不是一个字符,它是一个数字!
'a'
只是一个数字的简写。
所以在一个数字中添加两个字符结果。
看看这个关于添加字节的问题,虽然是违反直觉,但是同样的事情。
在4.1.5节(积分types)中定义了char
另一个相关位是整型:
对于二进制
+
…操作符,操作数被转换为T
types,其中T
是int
,uint
,long
和ulong
,可以完全表示两个操作数的所有可能值。
所以对于char
,都被转换为int
,然后添加为int
s。
重点是,许多C#概念来自C ++和C.
在这些语言中,单个字符常量(比如'A')被表示为它们的Ascii值,尽pipe人们可能期望它的types不是char而是int(是的,'A'是一个int,与写65相同)。
因此,所有这些值的添加就像写了一系列ASCII字符码,即
var pr= 82 + 71 + 66 + ...;
这已经是C / C ++在某个时候的一个devise决定(它可以用C来回溯到70年代)。
来自MSDN :
隐式转换可能在很多情况下发生,包括方法调用和赋值语句。
char可以隐式转换为ushort,int,uint,long,ulong,float,double或decimal。 因此,赋值操作将char转换为int。
char
或System.Char
是一个整型:
表示无符号16位整数的整数types,其值介于0和65535之间。该types的可能值集合对应于Unicode字符集。
这意味着它的行为与uint16
或System.UInt16
完全相同,并且使用+
运算符添加字符因此会添加整数值,因为+
运算符不会在char
重载。
要将各个字符连接成一个string,请使用StringBuilder.Append(char)
或new String(char[])
。
如前所述,这是因为一个字符的Int32值包含其Unicode值。
如果你想把字符连接成一个string,你可以执行以下操作之一:
将一个字符数组传递给一个新的string:
var pr = new string(new char[] { 'R', 'G', 'B', 'Y', 'P' });
使用StringBuilder:
StringBuilder sb = new StringBuilder(); sb.Append('R'); etc...
从string开始:
var pr = string.Empty + 'R' + 'G' + 'B' + 'Y' + 'P';
将每个string转换为一个string(或者只是第一个string也可以):
var pr = (string)'R' + (string)'G' + (string)'B' + (string)'Y' + (string)'P';
它不应该是因为这将是低效的。 如果有人想像这样连接字符,他们应该使用string生成器。 否则,每个添加都会创build一个临时内存来存放concatinated部分string,这意味着在您的示例中将不得不发生4个临时内存分配。
Char是一个16位整数值的文本表示。 你只是一起添加ints。 如果你想连接字符,你必须将它们转换为string。
1)定义(MSDN):
char关键字用于声明一个16位字符,用于表示世界上大部分已知的书面语言。
2)为什么char类似数字types?
A char can be implicitly converted to a numeric type.
char比string更接近整数。 一个string只是一个char对象的集合,而一个整数可以表示一个char,反之亦然。
3)例子
你可以简单地把你的第一个字符转换成一个string,来胜过你的编译器:
var pr = 'R'.ToString() + 'G' + 'B' + 'Y' + 'P';
你也可以定义一个char数组,然后使用string构造函数:
char[] letters = { 'R', 'G', 'B','Y', 'P' }; string alphabet = new string(letters);
如果你想单独打印一个字符,你总是必须把它转换成一个string,才能得到它的文本表示forms:
var foo1 = 'F'; MessageBox.Show(foo1.ToString());
为什么C#是这样devise的? 是不是添加两个字符的默认实现应该导致连接字符的string,而不是int?
你想要完成什么是不正确的。 一个string不是一个字符的附加,一个string是一个额外的说“单身”string。
所以“a”+“b”=>“ab”,如果考虑到,string的+操作符被重载,这是绝对正确的。 因此'a'代表ASCII字符65,完全一致地说,'a'+'b'是131。
因为一个char和另一个char可以超过charvariables所允许的最大值,所以这个操作的结果被转换成一个intvariables。
你假设char
是一个stringtypes。 char
的值可以用单引号之间的字符值来表示 ,但是如果有帮助的话,应该认为这是一个提供可读性的抽象,而不是强迫你作为开发者记住底层的价值。 实际上,它是一个数值types,所以你不应该期望任何string操作函数都适用。
至于为什么char + char = int
? 我不知道。 当然,向Int32
提供隐式转换会减less算术溢出,但是为什么short + short
没有被隐式types化为int
?