根据结构中的字段数编译时间开关生成

Compile time switch generation based on number of fields in structure

C++03如何在编译时获取所选结构的成员数?我正在试验 BOOST_FUSION_ADAPT_STRUCT 但我没有得到任何有效的例子。

我想在编译时生成 switch 语句,每个成员都有一个 case。所以假设我们有 3 个成员的结构然后我想生成这个开关:

switch(val)
{
   case 0:
       break;
   case 1:
       break;
   case 2:
       break;
}

在每个语句中,我都会调用带有一些参数的模板函数。此参数之一是结构成员。

我怎么能做这样的事情?

如果您使用 BOOST_FUSION_DEFINE_STRUCT 定义结构本身,boost 将以您可以轻松执行此操作的方式生成您的结构:

#include <boost/fusion/include/define_struct.hpp>
#include <boost/fusion/include/size.hpp>
#include <boost/fusion/include/for_each.hpp>


#include <iostream>
#include <string>

// demo::employee is a Fusion sequence
BOOST_FUSION_DEFINE_STRUCT(
    (),
    employee,
    (std::string, name)
    (int, age))

int main() {
  employee e{"hey", 5};
  int x = boost::fusion::size(e);
  std::cerr << x << std::endl;

  auto print = [] (auto v) { std::cerr << v << std::endl; };

  boost::fusion::for_each(e, print);
  return 0;
}

我修改了上面的代码以迭代结构的成员并应用通用函数。看起来这在功能上与您假设的案例陈述所做的相同。

您不能将此代码生成的“2”传递给预处理器宏的原因是预处理器首先运行,在代码之前,您不能将编译时或运行时生成的数字输入预处理器。

这个程序打印:

2
hey
5

参见:

  1. BOOST_FUSION_DEFINE_STRUCT in boost::fusion documentation

  2. size in boost::fusion documentation

  3. Iterating over Boost fusion::vector

经过长时间的搜索、阅读和发现 this article。我设法遍历从 0 到 count - 1 的成员(创建 switch 语句很容易)。

#include <iostream>
#include <string>
#include <vector>
#include <boost/fusion/include/adapt_struct.hpp>
#include <boost/preprocessor/repetition/repeat.hpp>
#include <boost/fusion/include/define_struct.hpp>
#include <boost/preprocessor/seq/size.hpp>
#include <boost/preprocessor/seq/seq.hpp>
#include <boost/preprocessor/seq/cat.hpp>

struct MyStruct
{
    int x;
    int y;
};

#define GO(r, data, elem) elem
#define SEQ1 ((int,x))((int,y))

BOOST_FUSION_ADAPT_STRUCT( 
    MyStruct,
    BOOST_PP_SEQ_FOR_EACH(GO, ,SEQ1)      
    )

#define PRINT(unused, number, data) \
    std::cout << number << std::endl;

int main()
{
    BOOST_PP_REPEAT(BOOST_PP_SEQ_SIZE(SEQ1), PRINT, "data")
}

现在 BOOST_PP_REPEAT 可以创建 case 语句。