在C中获得varargs的大小?

时间:2017-02-11 07:58:31

标签: c variadic-functions

我正在尝试将一些Java代码转换为C. Java代码如下:

public static int minimum( int... minimum ) {

    assert( minimum.length > 0 );

    if ( minimum.length > 0 )
     .... // some code that i am able to translate to C without any hassle
}

现在我了解如何使用stdarg.h标头并使用提供的宏在C中使用varargs。但是我坚持做minimum.length部分。

我试过strlen但是终端给了我一个与指针转换警告不兼容的整数。在C中有什么方法可以复制与Java相同的东西吗?

2 个答案:

答案 0 :(得分:5)

不是直接的,正如@MichaelBurr指出的那样,你需要传递元素的数量或使用哨兵。

执行此操作的间接方法是使用复合文字:

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

#define minimum(...) fnminimum(sizeof((int []) {__VA_ARGS__}) / sizeof(int), __VA_ARGS__)

static int fnminimum(int n, ...)
{
    int num, min = INT_MAX;
    va_list ap;

    va_start(ap, n);
    while (n--) {
        num = va_arg(ap, int);
        if (num < min) {
            min = num;
        }
    }
    va_end(ap);
    return min;
}

int main(void)
{
    int a = 1;

    printf("%d\n", minimum(2, 30, 7, a++, 4));
    return 0;
}

使用NARGS macros的另一种(丑陋)方法(限于N args):

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

#define NARGS_SEQ(_1,_2,_3,_4,_5,_6,_7,_8,_9,N,...) N
#define NARGS(...) NARGS_SEQ(__VA_ARGS__, 9, 8, 7, 6, 5, 4, 3, 2, 1)

#define minimum(...) fnminimum(NARGS(__VA_ARGS__), __VA_ARGS__)

static int fnminimum(int n, ...)
{
    int num, min = INT_MAX;
    va_list ap;

    va_start(ap, n);
    while (n--) {
        num = va_arg(ap, int);
        if (num < min) {
            min = num;
        }
    }
    va_end(ap);
    return min;
}

int main(void)
{
    printf("%d\n", minimum(2, 30, 7, 1, 4));
    return 0;
}

输出:

1

答案 1 :(得分:2)

没有内置的方法来获取在C中传递的vararg参数的数量。

您需要执行以下操作之一:

  • 明确传入计数,
  • 隐式传入一个计数(由->通过转换说明符的数量确定)
  • 或使用标记值(例如printf()NULL)来表示vararg列表的结尾

我已经看到使用宏和0标识符的方案在调用函数时自动将标记放在varargs列表的末尾。