C++ Boost.Fusion 中的可变参数宏?
因此,根据这个答案,C++不支持可变参数宏,并且 C++ 标准没有在任何地方提到可变参数宏。我知道 C99 使用 __VA_ARGS__
引入了可变参数宏,并且某些 C++ 编译器(如 GCC)甚至提供了扩展以允许在 C++ 中执行此操作,但事实是可变参数宏根本不是标准 C++ 的一部分。
现在,Boost.Fusion 中有一个功能,您可以使用 BOOST_FUSION_ADAPT_STRUCT
宏。这允许您像使用 Fusion 序列一样使用您的类或结构。
下面是一个如何使用它的示例(取自 Boost 文档):
namespace demo
{
struct employee
{
std::string name;
int age;
};
}
// demo::employee is now a Fusion sequence
BOOST_FUSION_ADAPT_STRUCT(
demo::employee,
(std::string, name)
(int, age))
现在,如果没有可变参数宏,这段代码怎么可能呢? BOOST_FUSION_ADAPT_STRUCT 宏似乎可以接受任意数量的参数,因为它可以与任何任意用户定义的类或结构一起使用。
我知道 Boost 以以有趣的方式弯曲 C++ 而闻名,但如果没有编译器支持,这似乎完全不可能。那么 Boost.Fusion 到底发挥了什么样的魔力来实现这一目标呢?
PS:是的,我知道Boost是开源的。我做的第一件事就是查看源代码。它似乎正在使用 Boost 预处理器库以某种方式连接宏。但我不明白这如何适用于任意数量的参数,并且源代码是非常密集的预处理器代码集合,非常难以理解。
So, according to this answer, C++ doesn't support variadic macros, and the C++ standard doesn't mention variadic macros anywhere. I know that C99 introduced variadic macros with __VA_ARGS__
, and certain C++ compilers (like GCC) even provide extensions to allow this in C++, but the fact remains that variadic macros simply aren't part of standard C++.
Now, there's a feature in Boost.Fusion where you can bind a Fusion sequence to an arbitrary class or struct using the BOOST_FUSION_ADAPT_STRUCT
macro. This allows you to use your class or struct as if it was a Fusion sequence.
Here is an example of how this is used (taken from the Boost docs):
namespace demo
{
struct employee
{
std::string name;
int age;
};
}
// demo::employee is now a Fusion sequence
BOOST_FUSION_ADAPT_STRUCT(
demo::employee,
(std::string, name)
(int, age))
Now, how is this code possible without variadic macros? The BOOST_FUSION_ADAPT_STRUCT
macro seems to take an arbitrary number of arguments, since presumably it can work with any arbitrary user-defined class or struct.
I know that Boost is famous for bending C++ in interesting ways, but this seems outright impossible without compiler support. So what sort of wizardry is Boost.Fusion doing to pull this off?
PS: Yes, I know Boost is open source. The first thing I did was to look at the source code. It seems to be using the Boost Preprocessor library to somehow concatenate macros. But I don't understand how this can work for any arbitrary number of arguments, and the source code is a very dense collection of preprocessor code which is very difficult to understand.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
这是一个带有两个参数的单个宏:
参数 1:demo::employee
参数 2: (std::string, name)(int,age)
参数 2 与字符串连接以形成另一个宏调用,该调用也采用 2 个参数:
This is a single macro which takes two arguments:
Argument 1: demo::employee
Argument 2: (std::string, name)(int, age)
Argument 2 is concatenated with a string to form another macro invocation which also takes 2 parameters: