我有一个玩具示例,我想在架构上进行修改以删除 on 的类型Processor
依赖EmitterT
:
#include <iostream>
#include <utility>
using namespace std;
struct Emitter {
void e(int) { cout << "emitting int\n";}
void e(double) { cout << "emitting double\n";}
void e(char*) { cout << "emitting char*\n";}
void e(const char*) { cout << "emitting const char*\n";}
};
template <typename EmitterT>
struct Processor {
Processor(EmitterT e) : e_{e} {}
template <typename T>
void process(T&& value) {
cout << "some processing... ";
e_(std::forward<T>(value));
}
EmitterT e_;
};
template<typename Emitter_>
Processor<Emitter_> makeProcessor(Emitter_ e) { return Processor<Emitter_>(e);}
int main() {
Emitter em;
auto p = makeProcessor([&em](auto v){em.e(v);});
p.process(1);
p.process("lol");
return 0;
}
动机
我想将负责利用处理结果的部分与处理本身分离。类Emitter
结构给了我,所以我必须支持重载函数。
我想将 lambda 函数传递给将使用它的处理器。有点像回调机制,但它必须是通用的 lambda,才能支持重载。
我试过的:
我编写的示例有效,但它取决于Emitter
作为模板参数的类型。我不喜欢Processor
基于Emitter
. 它也具有传染性,我有一个真正的Processor
等级制度,并且Emitter
传播得差不多const
或更糟。
阅读https://stackoverflow.com/a/17233649/1133179后,我尝试使用以下结构作为成员:
struct EmitterC {
template<typename T>
void operator()(T value) { }
};
但是当将其用作普通参数时,我无法找到一种推迟执行Emitter
after的方法。Processor
它使用前向声明和引用来解决,EmitterC&
但它只支持一个发射器定义。我能想出的唯一方法是删除 lambda,并EmitterC
为我期望的每种类型进行虚拟重载Emitter
并将其用作基类。
那么,有没有办法将(通用)lambda 作为参数传递,以便该Processor
类型不依赖于Emitter
?
我仅限于 c++14,但如果有更好的支持,我也对更现代的标准感兴趣。