我有时会故意省略宏观论点。例如,对于类似函数的宏,如
#define MY_MACRO(A, B, C) ...
我可以称之为:
MY_MACRO(, bar, baz)
技术上还有3个论点;只是第一个是“空的”。这个问题不是关于可变参数的宏。
当我这样做时,我在使用-ansi
(又名-std=c++98
)进行编译时会收到来自g ++的警告,但是当我使用-std=c++0x
时却没有。这是否意味着新的宏args在新的C ++标准中是合法的?
这是我的全部问题,但期待“你为什么要这样做?”回复,这是一个例子。我喜欢保持.h文件不被函数体整理,但是在.h文件之外实现简单的访问器是很乏味的。因此,我写了以下宏:
#define IMPLEMENT_ACCESSORS(TEMPLATE_DECL, RETURN_TYPE, CLASS, FUNCTION, MEMBER) \
TEMPLATE_DECL \
inline RETURN_TYPE* CLASS::Mutable##FUNCTION() { \
return &MEMBER; \
} \
\
TEMPLATE_DECL \
inline const RETURN_TYPE& CLASS::FUNCTION() const { \
return MEMBER; \
}
我将其用于包含名为int
的{{1}}的类模板:
int_
对于非模板类,我不需要IMPLEMENT_ACCESSORS(template<typename T>, int, MyTemplate<T>, Int, int_)
,所以我省略了这个宏参数:
template<typename T>
答案 0 :(得分:14)
如果我理解正确,从C99开始就允许空的宏参数
的C ++ 0x(11)。
C99 6.10.3 / 4说:
...参数的数量(包括由...组成的参数) 没有预处理令牌)应该等于参数的数量......
和C ++ N3290 16.3 / 4有相同的陈述,而C ++ 03 16.3 / 10提到:
...任何参数都不包含预处理令牌,行为是 未定义。
我认为空参数由表示参数组成
上面没有预处理令牌
另外,6.10.3 in the Internationalation Programming Languages C rev。 5.10
说:
C99的新功能:现在也可以使用类似函数的宏调用 有空参数,也就是说,参数可能由no组成 预处理令牌。
答案 1 :(得分:8)
是。相关位是16.3 / 11
由最外部限制的预处理令牌序列 匹配括号形成类似函数的参数列表 宏。列表中的各个参数用逗号分隔 预处理令牌。
不要求单个参数恰好对应于一个标记。实际上,以下部分清楚地表明每个参数可以有多个标记:
在被替换之前,每个参数的预处理标记都是 完全宏观被取代,好像他们形成了其余部分 预处理文件
在您的情况下,一个参数恰好对应于零令牌。这不会引起任何矛盾。
[编辑] N1566改变了这一点,使C ++ 11符合C99。
答案 2 :(得分:4)
当我这样做时,我通常会发表评论来代替争论。
放置一个将扩展为空字符串的宏。
#define NOARG
...
MY_MACRO(/*Ignore this Param*/ NOARG, bar, baz)
PS。使用或不使用-std = c ++ 98标志的g ++没有任何警告。