【问题标题】:Why is 1 not greater than -0x80000000 [duplicate]为什么1不大于-0x80000000 [重复]
【发布时间】:2015-01-19 01:57:58
【问题描述】:

为什么 1 不大于 -0x80000000。我知道这与溢出有关。但是有人可以解释为什么吗? 0x80000000 不是我认为的常数吗?

assert(1 > -0x80000000);

C++ 中的断言触发器。这是为什么呢?


我很感谢提供的一些答案。但是 C++ 标准是否定义常量需要存储在 32 位整数中?为什么编译器不能识别 80000000 不适合 32 位整数并使用 64 位?我的意思是,最大的 32 位 int 可以是 0x7FFFFFFF。 0x80000000 显然比那个大。为什么编译器仍然使用 32 位?

【问题讨论】:

  • 你认为-0x80000000实际上代表了什么价值?
  • 闻起来像作业。
  • 因为你的unsigneds 有 32 个值位。
  • 环绕。 -0x80000000 无法在有符号的 32 位上表示。
  • 是在 C++ 中以 32 位 int 表示的整数常量吗?为什么编译不识别这不适合 32 位整数并使用 64 长来存储它?

标签: c++ c


【解决方案1】:

根据 C 和 C++ 标准,-0x80000000 不是整数常量。这是一个表达式,例如3 + 5。在这种情况下,它是由否定运算符操作的常量0x80000000。对于具有 32 位 ints 的编译器,0x80000000 不能表示为 int,但可以表示为 unsigned int。但是对无符号整数求反是(奇怪地)在无符号上下文中完成的。所以这里的否定实际上是没有效果的。

【讨论】:

  • 为什么要转换成unsigned int
  • @vsoftco 即使您的处理器恰好是 64 位,您的编译器也极不可能有 64 位 ints。
  • @vsoftco 它被视为(未转换为)unsigned int,因为它不能表示为int
  • @CommuSoft:int 不是 32 位的事实,并且依赖于该假设的程序是不可移植的。让你的程序在你关心的机器上以同样的方式运行是你的工作,而不是编译器的工作。
  • @Cheshar C 没有负十六进制常量。 (或负十进制常量!)如果需要负三,则将否定运算符- 应用于整数常量3。在您的示例中,0x800000000 是 long int(因为它太长,不能成为 intunsigned int),并且它的否定具有相同的类型。
【解决方案2】:

解决此问题的一种方法是使用您知道它可能能够正确表示和保留您的值的类型,这意味着您的表达式可以像这样固定

assert(1 > -0x80000000L);

assert(1 > -0x80000000LL);

这基本上是关于在 C++ 中为您的 supposedly integer 表达式使用标准后缀。

C++ 中整数类型的唯一 3 个标准后缀是 ulll,以及与小写对应含义相同的大写变体; ULLL

【讨论】:

    猜你喜欢
    • 2011-02-02
    • 1970-01-01
    • 2014-08-19
    • 2016-03-14
    • 2012-06-28
    • 1970-01-01
    • 1970-01-01
    • 2021-10-14
    • 2012-07-05
    相关资源
    最近更新 更多