【问题标题】:Equality operand behavior for unsigned and signed types [duplicate]无符号和有符号类型的相等操作数行为
【发布时间】:2012-10-27 21:55:05
【问题描述】:

可能重复:
Signed/unsigned comparisons

所以我有下面的代码,它将 unsigned int 设置为负数,然后将 unsigned int 与相同的负数进行比较。我得到的输出是“不等于”。我知道当将 unsigned int 设置为 -1 时,在这种情况下 unsigned int 的值设置为 255。

#include <stdint.h>
#include <iostream>

int main(int argc, char **argv)
{
  uint8_t test = 0;
  int8_t set = -1;

  test = set;

  if (test == set) {
    std::cout << "Equal";
  } else {
    std::cout << "Not Equal";
  }
}

但是,是什么导致相等操作数返回 false?这似乎与类似问题Signed/unsigned comparisons 的答案形成了直接对比,其中指出

许多二元运算符需要算术或 枚举类型导致转换并产生类似的结果类型 大大地。目的是产生一个通用类型,这也是 结果。这种模式称为通常的算术转换, 定义如下:

如果任一操作数是 long double 类型,则应转换另一个操作数 加倍。

否则,如果任一操作数为双精度,则应转换另一个操作数 加倍。

否则,如果任一操作数为浮点数,则另一个应转换为 浮动。

否则,积分促销 (4.5) 应在两者上执行 操作数.54)

然后,如果任一操作数是无符号长整数,则应转换另一个操作数 为无符号长。

否则,如果一个操作数是 long int 而另一个是 unsigned int, 那么如果一个 long int 可以表示一个 unsigned int 的所有值, unsigned int 应转换为 long int;否则两者 操作数应转换为 unsigned long int。

否则,如果一个操作数是长的,另一个应该被转换为 长。

否则,如果任一操作数是无符号的,则应转换另一个操作数 未签名。

因此根据这个答案,由于两个操作数都是无符号的,另一个应转换为无符号,并且相等应该通过。但它显然没有通过,正如在这个问题中已经回答的那样,它们都被提升为有符号整数。

【问题讨论】:

  • -Wall -Werror 会告诉你确切的原因。你有一个有符号/无符号的不匹配。在类型比较中。
  • @larsmans - 很容易忽略分配test = set
  • 小心使用像set这样的标准库名称作为变量。
  • @WhozCraig - 我知道代码是错误的,我只是在询问行为背后的基本规则。

标签: c++ c


【解决方案1】:

这确实是标准行为。与== 和大多数其他运算符一起使用时,小于int 的类型将提升为int。所以test 被提升为int,值为255。set 被提升为int,但它是一个负数,所以它的值在提升之前和之后都是-1。由于 255 不等于 -1,因此比较得出false

道德是:在比较中混合有符号和无符号类型时要小心。

【讨论】:

  • 感谢您的回答,这似乎与与无符号整数和有符号整数进行比较时的情况相矛盾。我的问题是为什么它不一样?
  • @umps - 有一个无符号类型的值不能表示为相应的有符号类型,反之亦然,因此对于大于或等于 int 大小的类型的规则执行不同的促销活动。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2018-08-14
  • 2020-10-30
  • 2014-02-01
  • 2019-06-10
  • 2017-04-05
  • 1970-01-01
  • 2016-12-08
相关资源
最近更新 更多