我有一个boost::mpl::vector
,现在需要一个模板(函数),其中"迭代"在找到第一个匹配(在运行时)之前的类型。类似于boost::fusion::find_if
的东西,但没有 sequence 是运行时值。
将它想象成这样:
typedef boost::mpl::vector<Foo, Bar> Types;
template< typename T >
struct Finder {
bool operator()() const;
};
struct Callback {
template< typename T >
void operator()();
};
Callback callback;
magic_find_if<Types, Finder>(callback);
在mpl / fusion中找不到这样的东西(找不到它)
我知道,Callback::operator()
的所有变体都将被&#34;实例化&#34;但这没关系。可以想象用Variadic模板来实现它,但遗憾的是我坚持使用C ++ 98。
答案 0 :(得分:1)
我建议将过滤器和回调组合成一个条件操作:
template <template<typename> class Finder, typename Callback>
struct ConditionOperation {
ConditionOperation(Callback cb = {}) : _callback(std::move(cb))
{ }
template <typename T>
void operator()(boost::type<T>) const {
if (Finder<T>()())
_callback.template operator()<T>();
}
private:
Callback _callback;
};
然后,在EricNiebler答案之后,你可以自由地写下:
ConditionOperation<Finder, Callback> op;
mpl::for_each<Types, boost::type<mpl::_1> >(op);
这是一个完整的演示
<强> Live On Coliru 强>
#include <boost/type.hpp>
#include <boost/mpl/vector.hpp>
#include <boost/mpl/for_each.hpp>
#include <iostream>
struct Foo { enum { id = 879 }; };
struct Bar { enum { id = 321 }; };
struct Qux { enum { id = 555 }; };
typedef boost::mpl::vector<Foo, Bar, Qux> Types;
template <typename T>
struct Finder {
bool operator()() const { return T::id > 500; }
};
struct Callback {
template<typename T> void operator()() const {
std::cout << __PRETTY_FUNCTION__ << "\n";
}
};
template <template<typename> class Finder, typename Callback>
struct ConditionOperation {
ConditionOperation(Callback cb = {}) : _callback(std::move(cb))
{ }
template <typename T>
void operator()(boost::type<T>) const {
if (Finder<T>()())
_callback.template operator()<T>();
}
private:
Callback _callback;
};
int main() {
using namespace boost;
ConditionOperation<Finder, Callback> op;
mpl::for_each<Types, boost::type<mpl::_1> >(op);
}
打印
void Callback::operator()() const [with T = Foo]
void Callback::operator()() const [with T = Qux]