注意,C和C++标准定义了两种实现:独立的和托管的。
C90托管环境
允许的表单1:
int main (void)
int main (int argc, char *argv[])
main (void)
main (int argc, char *argv[])
/*... etc, similar forms with implicit int */
评论:
前两个被显式声明为允许的形式,其他的被隐式允许,因为C90允许返回类型和函数参数为“隐式int”。不允许使用其他形式。
C90独立环境
允许使用任何形式或名称的main 2。
C99托管环境
允许的表单3:
int main (void)
int main (int argc, char *argv[])
/* or in some other implementation-defined manner. */
评论:
C99删除了“隐式int”,因此main()不再有效。
引入了一个奇怪的、模棱两可的句子“或以某种其他实现定义的方式”。这可以被解释为“intmain()的参数可能不同”或“main可以有任何实现定义的形式”。
一些编译器选择以后一种方式解释标准。可以说,人们不能轻易地通过引用标准本身来说明他们不符合标准,因为它是模棱两可的。
然而,允许main()的完全野生形式可能不是(?)这个新句子的意图。C99的基本原理(非规范性)意味着该语句引用了int main 4的附加参数。
然而,托管环境程序终止部分继续讨论main不返回int 5的情况。尽管该部分对于如何声明main并不是规范性的,但它肯定意味着即使在托管系统上,main也可以以完全实现定义的方式声明。
C99独立环境
允许使用任何形式或名称的main。
C11托管环境
允许的表单7:
int main (void)
int main (int argc, char *argv[])
/* or in some other implementation-defined manner. */
C11独立环境
允许使用任何形式或名称的main。
注意,在上述任何版本中,int main()从未被列为C的任何托管实现的有效形式。在C中,与C++不同,()和(void)有不同的含义。前者是一种过时的特征,可以从语言中删除。参见C11未来语言方向:
6.11.6函数声明器使用带有空括号的函数声明符(而不是原型格式参数类型声明符)是一种过时的特性。
C++03托管环境
允许的表单9:
int main ()
int main (int argc, char *argv[])
评论:
注意第一种形式中的空括号。在这种情况下,C++和C是不同的,因为在C++中,这意味着函数不带参数。但在C中,这意味着它可以采用任何参数。
C++03独立环境
启动时调用的函数的名称是实现定义的。如果它被命名为main(),它必须遵循所述的格式10:
// implementation-defined name, or
int main ()
int main (int argc, char *argv[])
C++11托管环境
允许的表单11:
int main ()
int main (int argc, char *argv[])
评论:
标准文本已更改,但含义相同。
C++11独立环境
启动时调用的函数的名称是实现定义的。如果它被命名为main(),它必须遵循所述的形式12:
// implementation-defined name, or
int main ()
int main (int argc, char *argv[])
工具书类
ANSI X3.159-1989 2.1.2.2托管环境。“程序启动”
程序启动时调用的函数名为main。这个实现没有声明此函数的原型。应为定义为返回类型为int且没有参数:
int main(void) { /* ... */ }
或具有两个参数(这里称为argc和argv,但可以使用任何名称,因为它们是本地的声明它们的函数):
int main(int argc, char *argv[]) { /* ... */ }
ANSI X3.159-1989 2.1.2.1独立环境:
在独立的环境中(C程序执行可能需要没有任何操作系统好处的地方)、名称和类型在程序启动时调用的函数的实现是定义的。
ISO 9899:1999 5.1.2.2托管环境->5.1.2.2.1程序启动
程序启动时调用的函数名为main。这个实现没有声明此函数的原型。应为定义为返回类型为int且没有参数:
int main(void) { /* ... */ }
或具有两个参数(这里称为argc和argv,但可以使用任何名称,因为它们是本地的声明它们的函数):
int main(int argc, char *argv[]) { /* ... */ }
或同等产品;9) 或在定义的某些其他实现中方式
国际标准编程语言-C的基本原理,修订版5.10。5.1.2.2托管环境-->5.1.2.2.1程序启动
main参数的行为,以及exit、main和atexit的交互作用(见§7.20.4.2)已被编入法典,以抑制argv表示中的一些不必要的变化字符串,以及main返回值的含义。
argc和argv作为main参数的规范承认了广泛的先前实践。argv[argc]必须是空指针,以便为列表末尾提供冗余检查,这也是基于常见的做法。
main是唯一一个可以用零或两个参数声明的函数。(其他函数的参数数量必须在调用和定义之间完全匹配。)这种特殊情况只是认识到当程序不访问程序参数字符串时,将参数保留为main的普遍做法。尽管许多实现支持两个以上的主要论点,但标准既不支持也不禁止这种做法;用三个参数定义main的程序并不严格符合(见§J.5.1.)。
ISO 9899:1999 5.1.2.2托管环境-->5.1.2.2.3程序终止
如果主函数的返回类型是与int兼容的类型,那么从初始调用到主函数的一个返回就相当于用主函数返回的值作为其参数调用退出函数;11) 到达终止主函数的}返回值0。如果返回类型与int不兼容,则返回到主机环境的终止状态未指定。
ISO 9899:1999 5.1.2.1独立环境
在一个独立的环境中(在这种环境中,C程序的执行可能没有任何操作系统的好处),程序启动时调用的函数的名称和类型是由实现定义的。
ISO 9899:2011 5.1.2.2托管环境->5.1.2.2.1程序启动
本节与上述C99节相同。
ISO 9899:1999 5.1.2.1独立环境
本节与上述C99节相同。
ISO 14882:2003 3.6.1主要功能
实现不应预先定义主功能。该功能不应过载。它应该具有int类型的返回类型,否则它的类型是实现定义的。所有实现应允许以下两种主要定义:
int main() { /* ... */ }
和
int main(int argc, char* argv[]) { /* ... */ }
ISO 14882:2003 3.6.1主要功能
它定义了独立环境中的程序是否需要定义主功能。
ISO 14882:2011 3.6.1主要功能
实现不应预先定义主功能。该功能不应过载。它应该具有int类型的返回类型,否则它的类型是实现定义的。所有实施应允许两者-返回int和-返回int的(int,指向指向char的指针)函数作为主要类型(8.3.5)。
ISO 14882:2011 3.6.1主要功能
本节与上述C++03节相同。