代码之家  ›  专栏  ›  技术社区  ›  josh

打印数组元素

  •  3
  • josh  · 技术社区  · 14 年前

    以下C程序的预期输出是打印数组元素。但实际上,当它运行时,它不会这样做。

    #include<stdio.h>
    
    #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;
    }
    

    原因是什么?

    6 回复  |  直到 11 年前
        1
  •  5
  •   John Kugelman Michael Hodel    14 年前

    当你做比较的时候 d <= (TOTAL_ELEMENTS-2) A 类型转换 执行。 d 属于类型 signed int 虽然 (TOTAL_ELEMENTS-2) 属于类型 size_t ,它是无符号类型。c的规则是,当一个运算符有一个有符号参数和一个无符号参数,而无符号参数的大小大于或等于有符号参数时,则有符号参数转换为无符号参数。

    也就是说,比较结果是:

    (size_t) d <= (TOTAL_ELEMENTS-2)
    

    因为 西泽特 是未签名的, (size_t) -1 是一个非常非常大的数字,不再是-1。32位的 西泽特 它将是2 三十二 -1=4294967295。

    要解决此问题,可以显式地将右侧强制转换为带符号的int:

    d <= (int) (TOTAL_ELEMENTS-2)
    

    或者,更好的方法是,去掉奇怪的负索引等等。

    为供将来参考,请打开 编译器警告 你可以。例如,如果打开,GCC将打印警告 -Wall -Wextra :

    $ gcc -o arrayprint -Wall -Wextra -ansi arrayprint.c 
    arrayprint.c: In function ‘main’:
    arrayprint.c:11: warning: comparison between signed and unsigned
    
        2
  •  6
  •   zvrba    14 年前

    TOTAL_ELEMENTS 是未签名的。-1,当转换为无符号时,是一个非常大的数字,不小于6。因此,循环永远不会运行。

        3
  •  3
  •   Roland Illig    14 年前

    起初,我不知道。但当我使用gcc编译它时,很明显:

    $ gcc -Wall -Wextra -Os a.c
    a.c: In function `main':
    a.c:11: warning: comparison between signed and unsigned
    

    因此,您可以进行如下比较:

    (int) -1 <= (size_t) 5
    

    由于其中一个类型是有符号的,另一个是无符号的,所以首先需要将它们转换为公共类型。在这种情况下,它是 size_t . 这使得:

    (size_t) -1 <= (size_t) 5
    

    现在 -1 不能用无符号类型表示。因此,2^32(或多个位 西泽特 已添加)使其成为4294967295。所以比较的真正原因是:

    4294967295 <= 5
    

    那就是 false 因此,循环体永远不会执行。

        4
  •  1
  •   Frerich Raabe    14 年前

    原因是循环从未执行过。这是因为 TOTAL_ELEMENTS 返回大小为“T”的无符号类型。

    你可以通过铸造来解决这个问题 (TOTAL_ELEMENTS-2) 到国际

        5
  •  0
  •   reece    14 年前

    您需要执行以下操作:

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

    作为 sizeof(...) 生成无符号值。

        6
  •  0
  •   XCS    14 年前

    简单改变

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

    #define TOTAL_ELEMENTS (int)(sizeof(array)/sizeof(array[0]))-2