c++ 中的 dynamic_cast 有啥替代方法吗?
Posted
技术标签:
【中文标题】c++ 中的 dynamic_cast 有啥替代方法吗?【英文标题】:Is there any alternative to dynamic_cast in c++?c++ 中的 dynamic_cast 有什么替代方法吗? 【发布时间】:2019-10-24 18:13:13 【问题描述】:如果 RTTI 在某些编译器环境中被禁用,我想知道这一点。
用例:
我在我的代码中使用了它,它在我的机器上运行,但在集成测试期间,代码无法正常运行,而是崩溃了。
我认为如果 RTTI 不存在,它会返回 null,这在我的代码中已处理,但行为出乎意料。
我应该检查什么才能优雅地终止它?
此外,当我使用 dynamic_cast 的包装器(在我们的内部框架中定义)时,它工作得很好。该包装器需要什么样的实现来满足这个要求?
【问题讨论】:
This gist shows how to detect whether RTTI is enabled. 也许你应该发布代码和编译器信息。你dynamic_cast
是指针还是引用?
使用virtual
函数试过被拒绝了?
如果 RTTI 被禁用,你希望 dynamic_cast
有什么行为?
@M.M:我想要一些功能相似但没有 RTTI 的东西。我发现,我们有一些内部专有框架可以做到这一点。我想虽然这里提供的解决方案非常优雅,但没有这样的选择。谢谢。
【参考方案1】:
Raymond Chen 在评论中留下了精彩的 link 关于如何检测 RTTI 是否启用的评论。
要完成此操作,您可以使用以下命令覆盖 dynamic_cast
:
#if !defined(RTTI_ENABLED)
#define dynamic_cast _NullPtrTFn
#endif
template <typename T1, typename T2>
T1* _NullPtrTFn(T2* p)
static_cast<T1*>(p); // try fail to compile (https://godbolt.org/z/hcjKki)
return static_cast<T1*>(nullptr);
【讨论】:
这和#define dynamic_cast static_cast
有区别吗?
@M.M 是的,因为 1) 如果您尝试向下转换,static_cast 会引发编译错误 2) 在向上转换的情况下,它不会返回 nullptr
"如果你尝试向下转换,static_cast 会抛出编译错误" - 不正确
这如何编译?真正的dynamic_cast
只有1个模板参数,而_NullPtrTFn
有2个,所以当RTTI_ENABLED
未定义时,不应该使用dynamic_cast<T>
编译失败吗?我认为像template <typename T> T* _NullPtrTFn(void*) return nullptr;
这样的实现会更好,是吗?
@tuket 好吧,我想我没有考虑到Template Argument Deduction。谢谢。以上是关于c++ 中的 dynamic_cast 有啥替代方法吗?的主要内容,如果未能解决你的问题,请参考以下文章
有啥好的 C++ 项目构建工具可以替代 make 吗? [关闭]
C++中的new/delete构造/析构函数dynamic_cast分析
C++:即使转换的对象不是 NULL,dynamic_cast 也会导致 SEGFAULT。怎么会这样?