为什么有些类型没有文字修饰符

时间:2011-12-29 17:57:11

标签: c# literals

例如,为什么long int有一个文字修饰符,但是short int没有?我在本网站上提到以下问题:C# compiler number literals

通常,C#似乎是一种设计良好且一致的语言。可能有一个强有力的理由为某些类型提供文字修饰符,但不是所有类型。它是什么?

6 个答案:

答案 0 :(得分:35)

  

为什么long int有一个文字修饰符,但是short int不是?

问题是“为什么C#没有此功能?”这个问题的答案总是一样的。默认情况下,功能未实现; C#没有该功能,因为没有人设计,实现并将该功能发送给客户。

缺少功能不需要理由。相反,所有功能必须通过证明其好处超过其成本来证明。作为提出该功能的人,您有责任描述您认为该功能有价值的原因;我有责任解释为什么不是。

  

可能有充分的理由为某些类型提供文字修饰符,但不是全部。它是什么?

现在这是一个更负责任的问题。现在的问题是“长期以来文字后缀的合理性,为什么这也不是短文中类似文字后缀的理由?”

整数可用于各种目的。您可以将它们用作算术数字。您可以将它们用作位标志集合。您可以将它们用作数组的索引。还有很多特殊用途。但我认为可以公平地说,大多数时候,整数被用作算术数字。

通过普通程序以整数执行的绝大多数计算涉及的数字远远小于32位有符号整数的范围 - 大约+/- 20亿。在处理32位整数时,许多现代硬件都非常高效。因此,使数字的默认表示符号为32位整数是有意义的。因此,C#旨在使涉及32位有符号整数的计算看起来完全正常;当你说“x = x + 1”时,“1”被理解为带符号的32位整数,而且x也是好的几率,而且总和的结果也是。

如果计算是整数但不适合32位整数的范围怎么办? “长”64位整数是明智的下一步;它们在许多硬件上也很有效,并且长期有一个范围可以满足几乎所有没有进行涉及极大数量的重型组合的人的需求。因此,有一些方法可以在源代码中清楚简明地指出这里的文字将被视为一个长整数。

Interop场景或整数用作位域的场景通常需要使用无符号整数。同样,有一种方法可以清楚简明地指定此文字旨在被视为无符号整数。

所以,总结一下,当你看到“1”时,用户希望将它用作32位有符号整数的绝大部分时间都是好的。接下来最可能的情况是用户希望它是长整数或无符号整数或无符号整数。因此,每种情况都有简明的后缀。

因此,该功能是合理的。

为什么这不是短裤的理由?

首先,在短片合法的每个上下文中,使用整数文字已经合法。“short x = 1;”完全合法;编译器意识到整数适合短路并允许你使用它。

其次,算术永远不会在C#中做空。算术可以用ints,uints,longs和ulongs来完成,但是算术永远不会完成。短片提升为int并且算术是以整数形式完成的,因为正如我之前所说,绝大多数算术计算都适合于int 。绝大多数适合做空。现代硬件上的短算术可能较慢,它针对整数进行了优化,而短算术不会占用更少的空间;它将在芯片上以整数或多头完成。

你想要一个“长”后缀来告诉编译器“这个算法需要在longs中完成”,但是“short”后缀并不能告诉编译器“这个算法需要在短路中完成”因为那根本就不是一开始就是C#语言的一个特性。

提供长后缀和无符号语法的原因不适用于短路。如果您认为该功能有令人信服的好处,请说明好处是什么。没有任何好处来证明其成本,该功能将不会在C#中实现。

答案 1 :(得分:9)

根据MSDN

short x = 32767;
  

在前面的声明中,整数文字32767是隐式的   从int转换为short。如果整数文字不适合   如果存储位置较短,则会发生编译错误。

所以这是一个编译时功能。 short没有后缀,因为它永远不需要。

相关问题可能是:为什么longfloatdecimal确实有后缀?
简短的回答是i + 1i + 1L可以产生不同的值,因此具有不同的类型。

但是没有“短算术”这样的东西,short值在计算中使用时总是转换为int

答案 2 :(得分:4)

正如埃里克在评论中指出的那样,我的答案下面没有意义。我认为说无法在C#中表达一个简短的字面并且无法在IL中表达一个简短的文字有一个共同的原因(缺乏一个令人信服的理由来说明这个特征。)VB.Net显然有一个简短的说法。文字说明符,这很有趣(为了向后兼容VB语法?)无论如何,我在这里留下了答案,因为一些信息可能很有趣,即使推理不正确。


没有短文字,因为实际上没有任何方法可以在IL中加载短文字,IL是CLR使用的基础语言。这是因为所有“短”类型(任何小于int的类型)在加载到操作堆栈时都会隐式扩展为int。有符号和无符号同样是操作问题,并且实际上没有与操作堆栈上的活动数字“存储”。当你想在操作堆栈中将一个数字存储到一个内存位置时,'short'类型才会发挥作用,因此有IL操作转换为各种'short'类型(尽管它实际上仍然将数字扩展回int转换后;它只是确保该值适合存储到“短”类型的字段中。)

另一方面,长类型具有文字说明符,因为它们在操作堆栈上被区别对待。有一个单独的Ldc_I8指令用于加载常量长值。还有Ldc_R4(因此为什么你需要浮点数'f')和Ldc_R8(如果你使用没有说明符的十进制数字,C#选择它作为默认值。)十进制是一种特殊情况,因为它实际上不是IL中的原始类型;它只是在C#中有一个内置的常量说明符'm',它编译成一个构造函数调用。

至于为什么没有特殊的短操作(以及相应的短文字),这可能是因为大多数当前的CPU架构不能使用小于32位的寄存器,因此在CPU级别上没有区别值得利用。您可以通过允许“短”加载IL操作码来节省代码大小(以IL的字节数表示),但代价是抖动的额外复杂性;保存的代码空间可能不值得。

答案 3 :(得分:2)

由于short可以隐式转换为intlongfloatdoubledecimal;不需要文字修饰符。

考虑:

void method(int a) {}
void method2()
{
    short a = 4;
    method(a); // no problems
}

您可能会注意到charbyte也有文字修饰符,原因可能相同。

From    To
sbyte   short, int, long, float, double, or decimal
byte    short, ushort, int, uint, long, ulong, float, double, or decimal
short   int, long, float, double, or decimal
ushort  int, uint, long, ulong, float, double, or decimal
int     long, float, double, or decimal
uint    long, ulong, float, double, or decimal
long    float, double, or decimal
char    ushort, int, uint, long, ulong, float, double, or decimal
float   double
ulong   float, double, or decimal

答案 4 :(得分:1)

如果声明文字短,并使其大于Short.MaxValue,则会发生编译错误,否则文字将会很短。

答案 5 :(得分:0)

我“在短时间内工作”的时间是存储在数据库中的值。

它们是正整数值,很少会超过10到20.(一个字节或一个字节就足够了,但是如果代码重复使用的话,我认为有点过分会让我后悔自己的选择不同的方式)

该字段用于让用户对表中的记录进行排序。此表提供按“时间”排序的下拉列表或单选按钮列表(第一步,第二步,......)。

对C#不熟悉(并且在计算字节数时要记得很重要)我认为它会更有效率。我不对数值做数学。我只是对它们进行排序(并在记录之间进行交换)。到目前为止唯一的数学是“MaxInUse”+1(对于新记录),这是一个特例“++ MaxInUse”。这很好,因为缺少文字意味着“s = s + 2”必须是“s =(Int16)(s + 2)”。

现在我看到C#与其他整数一起工作有多烦人,我期望加入现代世界并浪费字节,只是为了让编译器满意。

但是,在我们的十大编程目标中,不应该“让编译器满意”排名第65位吗?

让编译器抱怨将整数“2”添加到任何INTEGER类型中是否有利于它?它应该抱怨“s = 123456”,但这是一个不同的情况。

如果有人必须处理数学和短裤,我建议你制作自己的文字。 (你需要多少人?)

short s1= 1, s2 = 2, s123 = 123;

然后s = s + s2只是有点烦人(并且对那些追随你的人感到困惑)。