C语言基本概念——正确理解C,不要被错误的题目误导

在进行C语言训练或做题时,我们可能会遇到一些看似简单但实则错误的题目。这些题目可能会误导我们对C语言基本概念的认识。因此,正确理解C语言并辨别题目中的错误至关重要。下面,举例说明题目错在哪。

1. 写出下列程序的运行结果。

#include 
int main()
{
  int a, b[4]={'a','b','c','d'};
  a= 'm';
  putchar(a);
  puts(b) ;  
  return 0;
}

本题给出的正确结果是ma。为什么?

分析: 第6行输出一个字符’m‘,第7行输出一个字符串,该字符串是“a”,因为b是一个整型数组,b的地址与b[0]的地址一样,如果整型数占4个字节,b[0]的4个字节在存储器中存储的数值从低地址到高地址分别是 ‘a'、0、0和0。如果把b[0]强制转换为一个字符串,则该字符串是“a",所以,本程序输出ma。

上面的分析头头是道,但是,它是错的,因为它只考虑到CPU字节序是小端序的情况,没有考虑到字节序为大端序时的情况。也就是说这个程序是认系统的,对于不同的系统其结果是不一样的。对于不同的计算机系统其采用的字节序可能是不同的,因此,上述分析不完全正确。对于大端序来说,这个程序的运行结果就是输出一个字符'm'。因为将b强制转换为字符串,其值为空串。下图是在大端序的计算机上运行的结果。程序的前几行用来判断计算机的字节序,从输出结果看可知是大端序的,在看本题的输出结果是'm',与上面分析一致。

C语言基本概念——正确理解C,不要被错误的题目误导_第1张图片

类似的题目还有:

下面程序的输出结果是_____。

#include 
int main(void)
{
    union {
      char c;
      int i;   
    }test;
    test.i = 0x1234;
    test.c = 'A';
    printf("%x",test.i);
    return 0;  
} 

本题提供的答案是 41 ,这个一个错的答案。

在小端序的计算机上运行,结果是1234。

下图是在小端序的计算机上运行结果的截图。

C语言基本概念——正确理解C,不要被错误的题目误导_第2张图片

在大端序的计算机上运行,结果是41001234。

下图是在大端序的计算机上运行结果的截图。

C语言基本概念——正确理解C,不要被错误的题目误导_第3张图片

2. 写出下列程序的运行结果。


#include 
int main()
{
  int x=1, y=0, a;
  a = (x-->y+x) ? 10: 20;
  printf("a=%d\n",a);
  return 0;
}

分析:表达式x-->y+x成立,则输出a=10,否则输出a=20。因x的数值为1,子表达式x--的值为1,子表达式y+x的值也为1,因此,x-->y+x不成立,即该表达式的值为0,因此,输出结果是a=20。

这个分析也是错的。如果在Dev C++环境下编译运行这个程序,输出结果为a=10。

C语言基本概念——正确理解C,不要被错误的题目误导_第4张图片

这是为什么?这是因为表达式x-->y+x存在未定义行为。因为子表达式x--的值为1,但其自减1的发生可能在y+x之前,或之后,如果在y+x之前发生,则x--等于1,y+x等于0,x-->y+x条件成立,如果在之后发生,则x-->y+x不成立。

对于存在未定义行为的表达式,那是潜在的bug,在编写程序时一定要避免使用。

参考文献:

[1]李红卫,李秉璋. C程序设计与训练(第四版)[M],大连,大连理工大学出版社,2023.

[2]https://pan.baidu.com/s/17ZXphwqySNIsIgcGtYMjvg?pwd=lhwc

[3]C语言基本概念——正确理解C,不要被错误的题目误导

 
 

你可能感兴趣的:(c语言,开发语言)