8 位和 16 位整数的算术运算
Posted
技术标签:
【中文标题】8 位和 16 位整数的算术运算【英文标题】:Arithmetic operations with 8 and 16 bit integers 【发布时间】:2014-09-15 20:57:37 【问题描述】:我明白为什么这会产生编译时错误:
short x = 1;
short y = 2;
short z = x + y; // compile-time error
我已经理解了为什么它运行时没有任何问题:
short x = 1;
short y = 2;
x += y; // all right, because of c# specs section 7.17.2
但我不知道为什么这也有效:
short x = (short)1 + (short)2;
我希望得到与第一个示例相同的编译时错误,但它运行成功...为什么?
【问题讨论】:
可能是因为在您的上一个示例中,编译器检测到一个常量值? 这实际上不是链接帖子的副本 - OP 特别指出了该帖子中的行为......(***.com/questions/4343624/…) + 运算符将返回(右/左??)上的任何类型 @Radiospace 这不一定是真的。在 C# 中,short + short 返回一个 int。 实际上恰恰相反。它需要一个演员,因为表达式很容易以一种无法察觉的方式溢出,并希望你承认你考虑过这个问题。他们想不出一个体面的语法来强制 += 强制转换。这些转换在 VB.NET 中不是必需的,但默认情况下会检查溢出。哪个“更好”,但非常昂贵。不是 C# 方式。 【参考方案1】:由于您使用的是常量值,编译器可以检测到它是允许的,在编译时对其进行评估,然后让它执行。生成的 IL 计算结果与键入 short x = 3;
相同。
请注意以下内容也有效(出于相同的原因):
const short x = 1;
const short y = 2;
short z = x + y;
但这失败了:
const short x = 32000;
const short y = 32001;
short z = x + y;
请注意,这在 C# 语言规范 6.1.9 隐式常量表达式转换中有所涉及:
如果常量表达式的值在目标类型的范围内,则可以将 int 类型的常量表达式(第 7.19 节)转换为 sbyte、byte、short、ushort、uint 或 ulong 类型。【讨论】:
【参考方案2】:你的最后一个 sn-p 只是编译成常量 3
。编译器不需要调用int
中的任何运算符,它只是在编译时计算并存储值。
和short x = 3;
一样
这是生成的IL
IL_0001: ldc.i4.3 //Load the constant 3 into evaluation stack
IL_0002: stloc.0 // stores the value in stack to x
【讨论】:
【参考方案3】:我不知道为什么这也有效:
short x = (short)1 + (short)2;
编译器在编译时对 rhs 表达式求值,可以证明结果在界限内。
【讨论】:
short x = 1 + 2;
怎么样?仍应输出一个int
,可以在编译时证明它适合short
。
@BenVoigt 可以正常工作,前提是您使用文字(常量)以上是关于8 位和 16 位整数的算术运算的主要内容,如果未能解决你的问题,请参考以下文章