我理解以下代码不起作用,因为我是运行时参数而不是编译时参数。但我想知道,是否有办法实现同样的目标。我有一个类列表,我需要调用一个模板函数,每个类。
void
GucTable::refreshSessionParams()
{
typedef boost::mpl::vector< SessionXactDetails, SessionSchemaInfo > SessionParams;
for( int i = 0; i < boost::mpl::size<SessionParams>::value; ++i )
boost::mpl::at<SessionParams, i>::type* sparam =
g_getSessionParam< boost::mpl::at<SessionParams, i>::type >();
sparam->updateFromGucTable(this);
}
}
有人可以建议我一个简单而优雅的方式来执行相同的操作吗?我需要遍历mpl :: vector并使用该类型调用全局函数,然后使用该参数进行一些运行时操作。
提前致谢, 戈库尔。
工作代码
typedef boost::mpl::vector< SessionXactDetails, SessionSchemaInfo > SessionParams;
class GucSessionIterator
{
private:
GucTable& m_table;
public:
GucSessionIterator(GucTable& table)
:m_table(table)
{
}
template< typename U > void operator()(const U& )
{
g_getSessionParam<U>()->updateFromGucTable(m_table);
}
};
void
GucTable::refreshSessionParams()
{
boost::mpl::for_each< SessionParams >( GucSessionIterator(*this) );
return;
}
答案 0 :(得分:3)
我只使用MPL作为BOOST_AUTO_TEST_CASE_TEMPLATE
的类型集合,所以我的知识非常有限。但是,我猜你可以使用for_each
来迭代MPL序列。
答案 1 :(得分:3)
您可以使i
成为编译时常量,并使用template recursion来迭代这些类。
答案 2 :(得分:0)
不幸的是,当涉及从编译时间世界到运行时世界的交叉时,你会经常发现MPL并不是很方便。
有一个Boost库:Boost.Fusion,其目的正是为了更容易地混合metatemplate编程和运行时。
如果你仔细阅读文档,你就会意识到他们并不害怕MPL,而是建立在它上面。作者甚至承认他们的序列在编译时操作中不如MPL那样有效......因此遵循以下准则: