C89与C99 GCC编译器比较

10

如果我使用c89和c99编译以下程序,是否会有区别?我得到了相同的输出。这两者之间真的有区别吗?

#include <stdio.h>

    int main ()
    {
      // Print string to screen.
      printf ("Hello World\n");
    }

gcc -o helloworld -std=c99 helloworld.c 
vs
gcc -o helloworld -std=c89 helloworld.c 

8
"gcc -std=c89"和"gcc -std=c99"并不完全符合各自的标准。加上"-pedantic"或"-pedantic-errors"可以获得接近完全符合标准的结果。 - Keith Thompson
3个回答

28
  • // 注释不是 C89 的一部分,但在 C99 中可以使用。
  • 在 C99 中,从 main() 掉出而没有返回任何值等同于 return 0;,但在 C89 中不是这样的。引自N1256(pdf),5.1.2.2.3p1:

    如果 main 函数的返回类型与 int 兼容,则从主函数的初始调用返回等同于调用 exit 函数,并将 main 函数返回的值作为其参数;到达终止 }main 函数返回值 0。

因此,在 C89 中,您的代码具有未定义的行为,在 C99 中则具有良好定义的行为。


6
理论上,应该有一个区别。使用“//”来标记注释不是C89的一部分,因此如果它正确地执行了C89规则,那么就会产生编译器错误(在-ansi -pedantic的情况下,可能会这样做,但我不确定)。
这给出了一个大致的特点:如果程序作为C89编译,则通常也会作为C99编译,并且给出完全相同的结果。 C99主要带来了一些新功能,这些功能在C89中不存在,因此您可以使用(例如)变量长度数组,而这在C89中是不允许的。
但是,您可能需要请求严格执行规则才能查看所有差异-C99旨在标准化现有实践,其中一些实践是gcc扩展,其中一些默认启用。

2
+1,干得好;//注释可能是C99中值得采用的唯一部分。 -ansi -pedantic会出现错误:main.c:5: error: expected expression before '/' token - Carl Norum
1
我不认为“//”注释有任何更多的用处,只是少了两个字符……这就像说C应该使用“.”来访问指向结构体的指针成员,而不是“->”,因为它可以节省打字。 - Joe D
1
@JoeD // 注释只捕获一行,这意味着它们不太可能被另一组注释无意中捕获或引起问题。此外,你关于 . 的论点有点傻;对于本质上相同的操作使用相同的运算符可能是一个好主意。 - Alice

2
在这个论坛上,我发现了这个链接:http://www.velocityreviews.com/forums/t287495-p2-iso-c89-and-iso-c99.html 。总结一下:C99是标准化的,有新的关键字、新的数组内容、复数、库函数等。由于有足够的时间去完善编译器,更多的编译器已经兼容C89标准。
A) ANSI X3.159-1989:这是最初的1989 C标准,日期为1989年12月,包含了Rationale。语言的主体在第3节中描述,而"C库"——stdio,函数等——在第4节中描述。
B) ISO 9899:1990:这是最初的ISO C标准。"ANSI"是美国国家标准协会,因此国际群体需要有自己的标准和不同的编号系统。他们只是采用了ANSI的1989年标准,删除了Rationale,并重新编号了章节(称之为"clause")。除了很少的例外简单加上三个数字即可,所以大部分语言在第6节中描述,而"C库"部分在第7节中描述。
C) ISO 9899:1999:这是新颖的"C99"标准,其中包括可变长度数组、灵活数组成员、新关键字如"restrict"和"_Bool"、"static"关键字的新语义、创建匿名聚合的新语法、新的复数类型、数百个新的库函数等。
ANSI立即将新的ISO标准"back-adopted"。我没有看到任何官方的"ANSI认可"声明,但考虑到常规的编号系统,我希望这将是ANSI标准号X3.159-1999。(编号系统非常明显:一旦一个标准出来,就会得到一个编号—— X.为ANSI,或只是一个数字为ISO——以及一个表示出版年份的后缀。对现有标准的更新重新使用该编号,加上新的年份。)
虽然X3.159-1989和9899:1990具有不同的年份和章节编号,但它们实际上是相同的,因此"C89"和"C90"实际上指的是同一种语言。因此,您可以说"C89"或"C90"并意味着相同的内容,即使对于了解所有细微差别的人也是如此。
原始1990年ISO标准还进行了几个小修订:"规范性补充1"和两个"技术勘误"(编号;给出技术勘误1和TC2)。这两个TC被认为是对标准措辞中小问题的"漏洞修复",而NA1则是一个实际的"更改"。实际上,TC对用户没有太大影响,而NA1增加了一整套人们可以使用的函数,因此NA1更重要。NA1于1994年发布,因此可以将"ISO 9899:1990 as modified by NA1"称为"C94"。我也看到它被称为"C95"。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接