已登录未签名的转化

时间:2009-01-31 13:11:34

标签: c

  

可能重复:
  A riddle (in C)

请参阅此代码

  #define TOTAL_ELEMENTS (sizeof(array) / sizeof(array[0])) 

  int array[] = {23,34,12,17,204,99,16}; 

  int main() 

  { 

      int d; 

      for(d=-1;d <= TOTAL_ELEMENTS-2;d++) 
          printf("%d\n",array[d+1]); 

      return 0;

  } 

现在这个循环不会运行。 sizeof()将返回无符号值,因此TOTAL_ELEMENTS具有无符号值。 现在,进入for循环,请告诉我,如果一元运算符' - '在signed int 2上工作或隐式转换发生在unsigned中,然后' - '运算符工作。

5 个答案:

答案 0 :(得分:8)

在您的示例中, d 在比较中转换为 unsigned int 。但-1不能表示为 unsigned int 值,因此它被转换为UINT_ MAX。要避免此行为,您可以通过预先添加(int)将比较的右侧转换为带符号的 int

有关C中整数转换的详细信息,请参阅Understand integer conversion rules

答案 1 :(得分:2)

d&lt; = TOTAL_ELEMENTS-2中没有一元运算符。

TOTAL_ELEMENTS-2缩减为二进制运算符为 - 的表达式。然后该表达式变为无符号,因为其操作数之一是无符号的。

在d&lt; = TOTAL_ELEMENTS-2的情况下,由于同样的原因,d's类型也被转换为unsigned int。

标准的相关部分是第6.3.1.8#1节(ISO / IEC 9899:1999),其中说:

“否则,如果具有无符号整数类型的操作数的等级大于或等于 等于另一个操作数的类型的等级,然后是操作数 有符号整数类型转换为带有unsigned的操作数的类型 整数类型。“

答案 2 :(得分:2)

是的,d在该表达式中也有一个无符号类型,因为促销,这就是循环失败的原因。

然而,问题是C编译器是否“认为”:

(unsigned) ((unsigned) 5 - (unsigned) 2)

即。将2提升为无符号,或者:

(unsigned) ((unsigned) 5 - (signed) 2)

即。减法取两种类型的操作数。当然,这没关系,因为两者的操作都是一样的。但是,重点是减法将返回一种类型的值,因此理论上它只能接受该类型的参数。所以它是第一个(unsigned int 2)。

P.S。 (-2)是一元的,而(5 - 2)是二元的。

答案 3 :(得分:0)

我怀疑无符号类型的sizeof()传播到表达式TOTAL_ELEMENTS-2,然后传播到d <= TOTAL_ELEMENTS-2的两个操作数。在(int)之前插入TOTAL_ELEMENTS juste可以解决问题。

答案 4 :(得分:0)

看,' - '运算符是一元的是一个愚蠢的事情。忘了它。它是二进制' - ',我意识到。

当2转换为无符号整数时,它变为无符号2,因此TOTAL_ELEMENTS-2的值等于无符号5,然后当d转换为无符号整数时,它得到一个大的正值,并且 所以循环失败了。

发生在这里吗?

是的,我没有写这个代码,这是我在网上找到的一些谜题。 谢谢你们。

相关问题