【问题标题】:Adding two signed or unsigned integers添加两个有符号或无符号整数
【发布时间】:2013-02-04 10:06:28
【问题描述】:

自从我上次在位和字节级别编程以来已经有很长时间了,我想确认一下我似乎记得的那些日子:

假设我有两个长度相等的整数(1、2、4、8 字节;没关系),我将它们相加:如果它们有符号,则和的逐位结果是否不同或未签名。换句话说:无论它们是有符号整数还是无符号整数,这些位最终会相同吗?

我的直觉和脆弱的记忆告诉我他们会的,但我只是想确认一下。谢谢。

【问题讨论】:

  • IIRC,虽然结果看起来不错,但 C/C++ 标准说整数溢出会导致未定义的行为。 编辑:无符号算术不会溢出,并且正常遵循环绕。
  • @nhahtdh:谢谢;没关系。我用 C++ 标记了它,因为我认为这会是一个很好的听众,但我将在另一种语言中使用它。

标签: c++ c integer twos-complement


【解决方案1】:

假设实现使用 2 的补码作为有符号整数的表示,那么结果将是相同的。在其他表示中,它们不会。

编辑

正如 cmets 中所指出的,有符号加法中的溢出是未定义的行为,这意味着在这种情况下对结果无话可说。

【讨论】:

  • 我希望我能给你投票两次:一次是为了回答,另一次是为了确认我的记忆力还不错:-)
  • @Eduardo,我将投第二票。好、简短、正确的答案。
  • 并且在添加时调用UB,它们也不会。
【解决方案2】:

我知道这个问题已经得到解答,但是我曾经使用过的所有处理器(大约有十几种不同的架构——我的意思是架构,而不是不同的风格)只有一种类型的 ADD 指令——它可能有不同的大小选项,但这是一条指令。这同样适用于减法。它在乘法和除法上有所不同,它通常具有有符号和无符号的变体 - 或者需要以某种方式对输入进行“符号调整”。

区分有符号和无符号的唯一其他指令是条件指令,例如“branch on less than”将有一个“unsigned less than”的变体和一个“signed less than”的变体(其中一个通常被称为“小于”以外的东西,例如“below”或“carry set”或一些这样的)。

【讨论】:

  • 这是一个很好的观点——即使标准说行为是未定义的,它也不太可能做一些底层 CPU 架构没有做的事情。这不是 C 和 C++ 滚动的方式。
  • @MarkRansom 这真的取决于上下文。上面 nhahtdh 链接的问题显示了编译器干预的示例。
  • 是的。当然,可能有一些 CPU 对“加法”和“减法”有不同的有符号和无符号指令,我还没有看到一个 [甚至听说过一个]。 C/C++ 规范由语言律师编写,必须满足各种奇怪的硬件。这并不意味着我们会经常看到这种类型的硬件...... ;)
  • MIPS 有两个(实际上是四个,因为添加立即数)ADD 指令:一个陷阱和一个不陷阱。
  • 是否会在有符号或无符号值的溢出时捕获?
猜你喜欢
  • 2013-10-27
  • 2013-11-11
  • 1970-01-01
  • 1970-01-01
  • 2015-02-24
  • 1970-01-01
  • 2019-04-26
  • 2010-09-19
相关资源
最近更新 更多