C++ main()如何处理不带省略号的可变数量的参数?
C++ main()如何处理不带省略号的可变数量的参数?,c++,c,C++,C,main()函数如何在不使用省略号(…)的情况下处理数量可变的参数?对于处理可变数量的参数,函数的最后一个参数应该是…,而main()函数的情况则不同。在C/C++main中采用两个参数,通常称为argc,和argv。argv参数是argcchar数组的数组。命令行参数在argv中传递给程序。在这个主题上,参数的确切数量有很多变化,但main的签名通常是 int main(int argc, char **argv); 基本上,main() int main(int argc, char **
main()
函数如何在不使用省略号(…
)的情况下处理数量可变的参数?对于处理可变数量的参数,函数的最后一个参数应该是…
,而main()
函数的情况则不同。在C/C++main中采用两个参数,通常称为argc
,和argv
。argv
参数是argc
char
数组的数组。命令行参数在argv
中传递给程序。在这个主题上,参数的确切数量有很多变化,但main的签名通常是
int main(int argc, char **argv);
基本上,main()
int main(int argc, char **argv)
int main(void)
系统可支持其他形式;通常情况下,环境也可用:
int main(int argc, char **argv, char **envp)
这些表格是固定的。唯一不寻常的是,一个系统必须支持前两个系统中的任何一个(有些系统也支持其他系统)
与POSIX不同,命令行参数的可变数量是通过指向字符串的指针数组(即上面的argv
)来处理的
另见:
:
你提到的两个链接非常清楚。这里列出了不同的可能方法,但没有提到实际使用的方法
在某种意义上,这并不重要;系统必须工作,生产“系统”的人必须让它工作。作为使用该系统的程序员,您不需要知道它是如何工作的;你可以简单地假设它确实有效
幕后,通常发生的是,调用“<代码>主代码())/>代码>的“开始”函数确实会有一些固定工作(在C++程序的情况下,特别是大量的固定工作),例如确保在“代码>主())//>开始之前必须执行的所有构造函数都被执行,但以固定顺序结束,例如:
exit(main(argc, argv, environ));
请注意,environ
是一个全局变量,extern char**environ代码>(这在POSIX定义的全局变量中是唯一的,因为没有头声明它),它包含指向环境变量的指针。“启动”代码必须确保已设置;因此,将environ
作为参数传递给main()
,非常简单
这将使用固定参数列表调用main()
,并在返回时调用exit()
。事实上,苹果更进一步,将第四个参数传递给main()
。如果被调用的函数被定义为intmain(void){…}
,它只会忽略传递的参数;如果它被定义为intmain(intargc,char**argv){…}
,它可以像往常一样访问命令行参数;如果它被定义为intmain(intargc,char**argv,char**envp){…}
,那么它也可以访问环境
通常,系统的设置是为了使额外的参数不会造成损害。这就是为什么C在其调用约定中不常见的原因,也是为什么被调用函数不清理推送到堆栈上的参数的原因——被调用函数不知道有多少参数被实际推送到堆栈上。它假定提供了它期望的代码,并且使用这些代码时没有问题,但是调用代码知道它推送了什么,所以它可以正确地清理。如果被调用函数需要N个参数,但调用方传递了M个参数和M我把这个问题解释为:main
怎么可能接受零个参数或两个参数
虽然细节显然依赖于实现,但在大多数实现中,默认的C调用约定是调用方清理堆栈。因此,无论main
的声明是什么,调用main
的代码都可以完全自由地将两个参数推送到堆栈上(argc
和argv
)。如果声明的main
没有参数,那么main
就不会访问它接收的参数的值。main
返回后,调用代码清除堆栈
应该指出的是,main
在这个意义上甚至都不是特别的。试试这个:
int printf();
int main() { printf("Hello, world!\n"); }
C编译器将很高兴地允许您调用printf
,即使缺少#include
指令,它也不知道实际需要多少参数printf
。大概,调用main
的代码在概念上是这样的:
int main(int argc, char** argv); /* declare "main" */
main(argc, argv); /* call "main" */
如果main
的定义实际上指定了零个参数,那么这仍然有效(尽管我相信如果您真的这样做了,从技术上讲这将是未定义的行为)
在C++的情况下,虽然<>代码>主< /代码>的链接未被标准所指定,但大多数实现简单地将其视为具有C链接,因此名称不被损坏,并且上面的所有内容仍然适用。
< P>它接受数组和数组长度设置为变量<代码> ARC<<代码>和<代码> ARGV < /P>
您可以在此处找到更多数据:
它得到一个指向字符数组的指针*…只需搜索main的签名即可
,也就是说,对于这个问题,这个网站上有很多问题需要解答。请注意,如果调用代码提供的参数超过被调用函数的预期,则不会导致问题,如果调用代码负责根据传递的参数数在返回后恢复堆栈。未使用的参数将被忽略。谢谢Jonathan。你提到的两个链接非常清楚。这里列出了不同的可能方法,其中哪一种是bei