我正在编写一个面向数据的编程注册表,它看起来有点像ECS注册表,工作方式如下:
void KillEnemy(EnemyList &enemies, ProjectileList &projectiles);
int main() {
auto registry
= Registry{}
.add_data(EnemyList{})
.add_data(ProjectileList{})
.add_data(TerrainList{});
//automatically call KillEnemy with proper arguments.
registry.call(KillEnemy);
}
我还没有弄清楚add_data
部分,但我认为可以用constexpr
和std::tuple
来完成。我目前的Registry
实现看起来像这样:
struct Registry {
std::tuple<int, double, float> data;
template<typename R, typename... Args>
R call(R (*f)(Args...)) {
return f(std::get<Args>(data)...);
}
};
这适用于函数指针,但如果我能将其与lambdas一起使用,则会更符合人体工程学。我想不出一个方法来推导参数。这可能吗?
更新:我刚刚写了add_data
。这是我目前的实现:
template <typename... DataType>
struct Reg {
std::tuple<DataType...> data;
template<typename R, typename... Args>
R call(R (*f)(Args...)) {
return f(std::get<std::remove_reference_t<Args>>(data)...);
}
template<typename T>
constexpr Reg<T, DataType...> add_data(T new_data = {}) &&{
return {std::tuple_cat(std::move(data), std::tuple<T>(new_data))};
}
};
int main() {
auto r = Reg<>{}
.add_data<int>()
.add_data<double>()
.add_data<float>();
r.call(system_with_duble);
r.call(system_with_float);
r.call(system_with_double_and_float);
}
1条答案
按热度按时间fdbelqdn1#
我刚想明白了