MST

星途 面试题库

面试题:C语言可变参数宏的复杂应用

定义一个可变参数宏 `SUM_ALL`,它可以接受任意数量的整数参数,并返回这些参数的总和。同时,要求在宏定义中处理参数数量为0的情况,返回0。请给出完整的宏定义代码,并简要说明实现思路。
26.5万 热度难度
编程语言C

知识考点

AI 面试

面试题答案

一键面试
#include <stdio.h>

// 可变参数宏定义
#define SUM_ALL(...) sum_all(__VA_ARGS__)

// 辅助函数,实际计算总和
static inline int sum_all(int first, ...) {
    va_list args;
    int sum = first;

    va_start(args, first);
    int num;
    while ((num = va_arg(args, int)) != 0) {
        sum += num;
    }
    va_end(args);

    return sum;
}

实现思路

  1. 可变参数宏 SUM_ALL:使用 __VA_ARGS__ 来代表可变参数列表,并将参数传递给辅助函数 sum_all
  2. 辅助函数 sum_all
    • 使用 va_list 类型的变量 args 来保存可变参数列表。
    • va_start 初始化可变参数列表,第一个参数为固定参数 first,从它之后开始解析可变参数。
    • 通过 va_arg 每次获取一个 int 类型的可变参数,并累加到 sum 中。当获取到值为 0 时停止循环,这里假设 0 作为结束标志。
    • 最后使用 va_end 清理可变参数列表。

在处理参数数量为0的情况时,由于宏定义 SUM_ALL(...) 展开后调用 sum_all(__VA_ARGS__),如果没有参数传入,__VA_ARGS__ 为空,调用 sum_all 时就不会传入任何有效参数,在 sum_all 函数中,first 没有被初始化,会导致未定义行为。为了处理这种情况,可以修改宏定义如下:

#include <stdio.h>

// 可变参数宏定义
#define SUM_ALL(...) (sizeof((int[]){__VA_ARGS__}) / sizeof(int) == 0? 0 : sum_all(__VA_ARGS__))

// 辅助函数,实际计算总和
static inline int sum_all(int first, ...) {
    va_list args;
    int sum = first;

    va_start(args, first);
    int num;
    while ((num = va_arg(args, int)) != 0) {
        sum += num;
    }
    va_end(args);

    return sum;
}

这里通过 sizeof((int[]){__VA_ARGS__}) / sizeof(int) 判断传入参数个数,如果为0,直接返回0;否则调用 sum_all 计算总和。