【发布时间】:2019-11-24 15:18:06
【问题描述】:
假设我们有以下两个函数:
void foo1(int p);
void foo2(int p, ...);
我想编写一个宏来根据参数的数量自动扩展为正确的宏。我使用了以下肮脏/骇人的方式,但我很好奇是否有针对此问题的干净解决方案。
#define SELECT(_1, _2, _3, _4, _5, _6, _7, _8, _9, _10, _11, _12, NAME, ...) NAME
#define foo(...) SELECT(__VA_ARGS__, \
foo2, foo2, foo2, foo2, \
foo2, foo2, foo2, foo2, \
foo2, foo2, foo2, foo1)(__VA_ARGS__)
这种方法只有在foo2 的参数数量不超过 12 个时才有效。这是我的解决方案的一个缺点。我正在寻找一种没有这种限制的方法。
更新 #1
真正的问题:在Android NDK中使用以下函数我们可以写日志:
__android_log_print(int prio, const char *tag, const char *fmt, ...);
__android_log_write(int prio, const char *tag, const char *text);
为了简化函数名称,我定义了一个名为 LOG 的宏:
#define LOG(...) __android_log_print(0, "test", __VA_ARGS__)
如果我给宏传递一个字符串文字,没关系,但是当我传递一个变量时,编译器会生成警告-Wformat-security。所以,我希望带有单个参数的宏调用扩展为__android_log_write,其他的扩展为__android_log_print。我的日志用例:1. 带/不带参数的字符串文字 2. 单参数变量char *。
【问题讨论】:
-
为什么不使用支持开箱即用的多态性的 c++ 呢? C 从未为这些情况而设计。
-
另一个问题:您要解决什么问题 - 宏将如何使用?具有 12 个(或更多)参数的函数将难以使用。是否所有参数都属于同一类型 - 您正在尝试传递 'list of int' ?
-
@dash-o 是的,我知道。我没有使用超过 12 个参数的函数。我只是好奇有更好的方法来解决这个问题,或者不使用 C 而不是 C++。我的整个项目都是用 C 编写的,我不会用 C++ 来解决这个简单的问题。
-
这两个函数分别在做什么?可能有一种方法可以将它们结合起来并避免任何宏诡计。
-
@dbush 我已经为我的实际问题添加了解释。
标签: c variadic-macros