在C++中,main的正确声明是什么?
C++中main函数的正确声明是什么?
C++语言标准(C++14)的确切措辞如下:
一个实现必须允许以下两种类型的main函数:
- 返回类型为int的函数()
- 返回类型为int的函数(int, 指向指针的char)
这表明,只要main函数的类型是int()或int(int, char**),就允许使用替代的拼写方式。因此,以下方式也是允许的:
- int main(void)
- auto main() -> int
- int main()
- signed int main()
- typedef char **a; typedef int b, e; e main(b d, a c)
需要注意的是,auto main() -> int
没有推导出返回类型。请注意"(auto main() {... is not allowed)"中的{,并请了解什么时候你还不足以添加有意义的内容。
C++中main函数的正确声明是什么?为什么main函数的返回类型应该是int?解决方法是什么?
根据C++标准文档中的描述,main函数应该有一个返回类型为int的返回值,但其它方面的类型是由具体的实现决定的。所有的实现都应该允许以下两种main函数的定义:
int main() { / ... / }
int main(int argc, char* argv[]) { / ... / }
在后一种形式中,argc应该是从程序所在的环境中传递给程序的参数个数。如果argc不为零,则这些参数应该以argv[0]到argv[argc-1]的形式提供,作为指向以空字符结尾的多字节字符串的指针。
以上是对C++标准文档中相关内容的整理。有没有关于为什么main函数的返回类型应该是int的具体原因呢?
原因是为了让调用进程知道是否应该将该进程视为成功。允许使用void作为返回类型会破坏这个模型。即使如果将void解释为"始终视为成功",这也没有意义。因为你无法判断进程是否实际上失败了,那你是否真的成功了呢?没有,所以返回int类型。
解决方法就是遵循C++标准文档中对main函数的要求,将其声明为int类型,并根据实际需要使用合适的参数列表。这样可以确保程序的正确性和可移植性。
在C++中,main函数必须作为全局命名空间中的非成员函数进行声明。这意味着它不能是一个类的静态或非静态成员函数,也不能放置在命名空间中(即使是未命名的命名空间)。
在C++中,main这个名字不是保留的,除了作为全局命名空间中的函数。你可以声明其他名字为main的实体,包括类、变量、枚举、成员函数和不在全局命名空间中的非成员函数。
你可以声明一个名为main的函数作为成员函数或在命名空间中,但这样的函数不会成为指定程序开始的main函数。
main函数不能被声明为static或inline。它也不能被重载;全局命名空间中只能有一个名为main的函数。
main函数不能在程序中使用:你不能在代码的任何地方调用main函数,也不能取它的地址。
main函数的返回类型必须是int。不允许使用其他返回类型。
有两种main函数的声明必须被允许:
int main() // (1)
int main(int, char*[]) // (2)
在(1)中,没有参数。
在(2)中,有两个参数,它们分别被约定地命名为argc和argv。argv是指向表示程序参数的C字符串数组的指针。argc是argv数组中的参数数目。
通常,argv[0]包含程序的名称,但这并不总是这样。argv[argc]保证是一个空指针。
请注意,由于数组类型参数(如char*[])实际上只是一个伪装的指针类型参数,下面这两种写法都是有效的,并且它们的意思是完全相同的:
int main(int argc, char* argv[])
int main(int argc, char** argv)
某些实现可能允许其他类型和数量的参数;你需要查看你的实现的文档以了解它支持什么。
main()函数期望返回0表示成功,返回非零表示失败。你没有义务在main()中显式地写一个return语句:如果你让main()没有显式的return语句返回,它就和写了return 0;一样。下面这两个main()函数的行为是相同的:
int main() { }
int main() { return 0; }
有两个宏,在cstdlib中定义,EXIT_SUCCESS和EXIT_FAILURE,也可以从main()中返回,分别表示成功和失败。
main()函数的返回值被传递给exit()函数,该函数终止程序。
请注意,所有这些仅适用于在托管环境中编译(非正式地说,你拥有一个完整的标准库,有一个运行程序的操作系统)。也可以将C++程序编译为自由环境(例如某些嵌入式系统的类型),在这种情况下,启动和终止完全是实现定义的,甚至可能不需要main()函数。但是,如果你在为现代桌面操作系统编写C++代码,你是在编译为托管环境。
据我所知,唯一保证的返回值是0、EXIT_SUCCESS(与0具有相同的效果)和EXIT_FAILURE。编辑:啊,好吧,可能会返回其他非零的状态值,但具有实现定义的意义。只有EXIT_FAILURE保证以某种方式被解释为失败值。
最好指定一下(以确保)这是关于C++的,因为Java/C#用户可能会感到困惑,因为这些语言实际上要求入口点是一个类(出于某种原因)。此外,旧的void main格式是从C遗留下来的吗?
问题的第一句话问,“在C++中,main函数的正确签名是什么?”问题标记了[c++]和[c++-faq]。如果Java或C#用户(或其他任何人)仍然感到困惑,我无能为力。C#要求Main是一个静态成员函数,因为它甚至没有非成员函数。即使是C89也要求main返回int。我对K&R C不太熟悉,不知道它的确切规则,但我猜测它也要求main返回int,因为没有返回类型等于隐式的int在K&R中相当普遍。
@James McNellis 你能解释一下为什么main的返回类型应该是int吗?
因为语言标准规定了返回类型必须是int。
@James McNellis 如果我使用void会有什么问题吗?
会有问题。你的代码将不是正确的C++代码,许多编译器将拒绝你的代码。
@James McNellis 哦!谢谢!你能否列举一些将拒绝void返回类型的main函数的编译器。到目前为止,我只用过Visual Studio C++(还有古老的turbo-c++),它通过了我的代码。
@James McNellis 为什么Microsoft的编译器通过了main函数的返回类型为void的代码。 (microsoft visual c++ 2010 express edition)
Visual C++允许使用void返回类型作为语言扩展。不允许使用它的编译器包括GCC和Comeau。
int main() {}版本一直是标准的一部分,还是最近才添加的?
在50多年前,它被添加到C中,在C++标准之前很久。
在一些不常见的平台(例如VAX/VMS)上,遵循非常旧版本的当时更模糊的C标准的编译器,EXIT_SUCCESS和EXIT_FAILURE只能作为exit()的参数可靠使用。从main()返回它们可能会产生意外的效果。现在标准已经被澄清,没有标准、可移植的方法来向主机环境返回完全任意的值;你必须使用特定于主机的扩展。