1. void main()、void main(void)、main()以及int main():
有人说前两种是完全不对的,只不过是编译器支持而已,其实这样说也不太对。实际上,C99已经允许为main声明“由实现定义的行为”(返回类型可以不是int型,也可以不是标准规定的参数),所以这样的行为是合法的。但是看起来很难看并且可移植性不好,最重要的是别人一看这样的代码就知道你C没学过关。
第三种是C89及之前的写法,现在已经过时。最后一种虽然在排斥void main()的人群中使用的比较普遍,但其实不属于函数声明,也被认为是一种过时的写法,C: A Reference Manual写到“所有现代的C代码都应该使用原型来编写。C99把旧式的非原型形式当成是过时的”,这种写法虽然不是无中生有,但起码也算正确。不过最标准的形式当然是int main(void)和int main(int argc, char *argv[])或int main(int argc, char **argv)。
2. i+++++i和k=i++ + ++i:
前者根本就无法通过编译,因为编译器把它看成了:((i++)++)(+i)。
后者k的值未定义,因为完整表达式末尾才是Sequence Point,i到底是何时自加何时做加法都不确定。
3.fflush(stdin):
fflush(stdin)是未定义的,在C: A Reference Manual写到:
“fflush函数清空于输出相关联的所有缓冲区,或者更新流参数。”
很多时候可以用如下代码代替它:
while (getchar() != '\n')
continue; // or ;
需要多次使用时可以自己定义一个宏:
#define FLUSH while (getchar() != '\n')
如果看不懂怎么回事那就说明你对getchar()了解过少。
4.sizeof是什么?
很多人认为sizeof是个函数,我建议你试试如下代码:
int i;
printf("%lu %lu\n", (unsigned long)sizeof(int), (unsigned long)sizeof i);
printf("%lu\n", (unsigned long)sizeof int);
呢?
5. a+=1一定与a=a+1等价?
如果这里的a不是普通变量而是a[i++]呢?
显然a[i++]+=1和a[i++]=a[i++]+1是不等价的,如果不信,可以通过i的值判断出来。
6. 对scanf()的认知不足。
我见过某网站的C语言视频教程里的教师写了一个这样的程序:
#include <stdio.h>
int main(void)
{
char c;
scanf("%c", &c);
while (c != 'J') {
printf("No!\n");
scanf("%c", &c);
}
return 0;
}
然后他发现程序有问题,输入除J外的字母后会出现两行的No!,当时他不知道怎么回事,没有办法,就打马虎眼过去了。
你知道怎么修改这个错误吗?
我见过很多人改,大多数人都是加了好长的代码。
其实呢,只要把scanf("%c", &c);改成scanf(" %c", &c);,这样就忽略了之前的空白字符,问题就被解决了。
如果你不知道怎么回事,说明你对scanf()了解不足。
7. C90?
很多人只知道传统C、C89和C99,于是见到C90就不知为何物,甚至认为是别人说错了。
C90即C89,因为1900年当时的ANSI C被进行少量编辑性修改后被转换成了国际标准ISO/IEC 9899:1990,所以C89也可以被称作C90.
另外,你知道C95吗?
8. getch()能随便用吗?
getch()及其相关头文件conio.h都不是标准库的一部分,不知道这一点的后果很显而易见,一个典型例子就是如果你在Linux上试图使用这个函数会发现根本无法使用。如果IDE没有设置程序暂停那么应该使用getchar()(有时候要用多次以把输入队列中的回车读完),即使你用getch你也应该知道它的来源。