使用gcc (或MinGW) 编译器,在C语言中,函数参数的数量是否有最大限制?

14

我知道如果遵循良好的实践,我永远不会达到这种限制。但是,我需要使用一个具有大量参数的自动生成函数(我无法更改它,我从别人那里接收该函数)。

因此:在gcc和MinGW中我最多可以使用多少个参数?

我在这里找到了有关C++语言规范的信息。以及这里有关C语言标准限制的信息。我感兴趣的是“真实世界”限制/实现细节的问题。尤其是在gcc和MinGW中。

此外:当达到这种限制时,我可以期望什么样的错误消息?并且当通过extern "C"声明在C ++应用程序中使用C代码时,这是否与“正常” C限制有所不同?可能存在其他限制,例如最大行长度或最大堆栈大小吗?

谢谢!


据我所知(而你提供的第一个链接也表明),C++中参数数量的限制为256个,而C语言则为127个。行长度不是问题,因为你可以将一行分成多行。只有当你的参数是巨大的结构体(而不是指向结构体的指针)时,堆栈大小才会成为问题。 - mch
3
这可能与ABI、处理器和编译器有关。我猜你用的是x86-64。从实际上来看,限制与堆栈帧和堆栈大小有关,因此我猜你可以传递几千个参数。我建议你进行简单的测试:写一个脚本生成N个参数的函数(例如计算所有参数的总和),并在另一个文件中编写一个“main”调用该函数。 - Basile Starynkevitch
为什么你希望你的代码处理超过指定语言最低限制?当然,你的代码需要强制执行某种限制,以便标记不合规的输入。如果使用规范的最低限制(127),会有什么损失呢? - chux - Reinstate Monica
@chux:目前有大约500个参数,它运行良好(尽管我有另一个错误找了几个小时,因此开始考虑其他原因-例如参数的最大数量)。它们不太可能变得更多,但当我开始思考这个限制时,这个话题引起了我的兴趣,所以我问了这个问题。这是由Matlab生成的包装函数,与S-Functions有关。但生成它不是我的任务(我会让其他人意识到C标准中的这个限制,以防万一)... - mozzbozz
如果参数数量过多,你的代码应该怎么做呢?或者你的代码需要接受任意数量的参数吗? - chux - Reinstate Monica
显示剩余2条评论
3个回答

17

《C标准5.2.4.1》规定:

4095 characters in a logical source line
127 parameters in one function definition
127 arguments in one function call

同时,如果您的参数是巨大的结构体,则堆栈大小(1MB - 8MB)是一个限制。

但是,所有这些限制都远离良好的实践。

https://gcc.gnu.org/onlinedocs/gcc-4.3.5/cpp/Implementation-limits.html 表示gcc有更高的限制(仅受可用内存限制)。


3
请注意,您提到的gcc文档仅涵盖C预处理器,虽然有一定指示作用,但并未真正涵盖此情况。 - Shafik Yaghmour
有一些微控制器的堆栈大小为256字节或更小。 - 12431234123412341234123

2
在C语言中有专门的库(stdarg.h)用于处理多个参数。通过使用这个库,你可以编写像这样的函数:
int a_function ( int x, ... )
{
    va_list a_list;
    va_start( a_list, x );
}

我认为没有特定的限制。


以下是如何使用该库的示例: (来源:http://www.cprogramming.com/tutorial/c/lesson17.html

#include <stdarg.h>
#include <stdio.h>

/* this function will take the number of values to average
   followed by all of the numbers to average */
double average ( int num, ... )
{
    va_list arguments;                     
    double sum = 0;

    /* Initializing arguments to store all values after num */
    va_start ( arguments, num );           
    /* Sum all the inputs; we still rely on the function caller to tell us how
     * many there are */
    for ( int x = 0; x < num; x++ )        
    {
        sum += va_arg ( arguments, double ); 
    }
    va_end ( arguments );                  // Cleans up the list

    return sum / num;                      
}

int main()
{
    /* this computes the average of 13.2, 22.3 and 4.5 (3 indicates the number of values to average) */
    printf( "%f\n", average ( 3, 12.2, 22.3, 4.5 ) );
    /* here it computes the average of the 5 values 3.3, 2.2, 1.1, 5.5 and 3.3
    printf( "%f\n", average ( 5, 3.3, 2.2, 1.1, 5.5, 3.3 ) );
}

尽管如@mch的回答所述,这似乎仍会遇到传递给单个函数调用的127个参数限制。 - Mark

-3

标准不知道,但在堆栈上,您可以传递任意数量的参数,如果通过寄存器传递,则数量受寄存器数量的限制。在C语言中,您可以通过堆栈按值传递结构。


8
C标准5.2.4.1规定:一个函数定义中最多可有127个参数,一个函数调用中最多可传递127个参数。 - mch

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