【发布时间】:2020-07-28 11:06:14
【问题描述】:
我有以下代码:
template<typename T>
class genericHandler{public: using evt_t = T;};
template<typename T>
class specialHandler : public genericHandler<T> { /* more stuff */ };
int main(int argc, char *argv[]) {
std::any any_var = specialHandler<int>{};
auto f = [&any_var](auto evtHandler) {
using EventType = typename std::remove_reference<decltype(evtHandler)>::type ::evt_t;
if(any_var.type() == typeid(EventType)) { std::cout << "yes" << std::endl; } else { std::cout << "no" << std::endl; }
};
auto h = specialHandler<int>{ };
f(h);
}
当被调用时,evtHandler 是非多态派生类型specialHandler。根据cppreference,我们有:
当应用于多态类型的表达式时,计算 typeid 表达式可能涉及运行时开销(虚拟表 查找),否则在编译时解析 typeid 表达式。
当我使用 gcc 和 -fno-rtti 编译时,我收到以下错误消息:
不能将“typeid”与“-fno-rtti”一起使用
RTTI 是运行时类型信息,在编译时可以推导出的非多态类型id 的情况下不需要。我错过了什么吗?
【问题讨论】:
-
你的类型是非多态的,但不幸的是你不知道
std::any的内部结构。 -
比较open-std.org/jtc1/sc22/wg21/docs/papers/2018/p1105r1.html。我可以确认它适用于 VS2017(并且禁用 rtti),但在 gcc 主干和 clang 主干上失败。
-
GCC 的
std::any在没有 RTTI 的情况下也能正常工作,只需使用any_cast检查它是否拥有该类型,而不是使用typeid,例如coliru.stacked-crooked.com/a/f68faa89814ea711 -
在回答下的评论中,您写了一些关于依赖周期的内容。请描述这个问题,因为显然这是您问题的实际根源,并且有很多技巧可以打破这种循环。