6

LLVM has it's own hand rolled alternative to RTTI that is a speed improvement over built-in RTTI and allows dynamic casting to classes with no vtable (dyn_cast). However, it can still be used in exactly the way that dynamic_cast<> is used though it does allow it to be used with more classes.

dyn_cast<> template documentation

LLVM is a reputable C++ project so this seems to fly in the face of the common saying that too many dynamic casts is a sign of bad design, also known as a code smell. Surely a better performing dynamic cast does nothing to improve its use in design than a standard dynamic_cast. So who is right here? Are there cases where large-scale use of dynamic casting is a good design choice in C++ code? Google turns up 690 occurrences of this kind of dynamic casting in the LLVM trunk source code.

Uses of dyn_cast<> in LLVM trunk

4

3 回答 3

7

虽然性能下降是避免dynamic_cast<>大型类层次结构的一个原因,但这并不是您可能想要避免它们的唯一原因。无论性能是否更好,都不应该dyn_cast<>因为这种说法而被鼓励使用。

另一方面,dynamic_cast<>当它是工作的最佳工具时,使用它绝对没有错。如果它的使用是合理的,并且是解决问题的最干净的方法,那么它总是正确的,不管“俗语”如何。

我当然不会因为流行项目使用dynamic_cast<>s、gotos 或任何其他不受欢迎的成语而避开它们。

于 2009-10-24T13:55:50.993 回答
1

I think dynamics casts are bad not because they are slow, but because they imply that your code is too tightly coupled.

于 2009-10-23T00:56:32.387 回答
-1

我只是快速浏览了 LLVM 文档中 dyn_cast 和 isa 的实现。

代码中的示例具有以下内容:

struct bar {
  bar() {}
private:
  bar(const bar &);

};
struct foo {
  void ext() const;
  /*  static bool classof(const bar *X) {
    cerr << "Classof: " << X << "\n";
    return true;
    }*/
};

template <> inline bool isa_impl<foo,bar>(const bar &Val) {
  errs() << "Classof: " << &Val << "\n";
  return true;
}

使用 a 调用测试,B并具有:

if (!isa<foo>(B1)) return;
if (!isa<foo>(B2)) return;

如果我正确理解发生了什么,则isa模板(由 使用dyn_cast)使用isa_implto link bar 和 foo 的显式特化。在给出的示例中,似乎isa<foo>(B1)返回 true!

无论如何,这与 dynamic_cast 的行为非常不同,所以我真的不认为你可以将它们相互比较。

显然,我可能误解了 LLVM 在做什么,所以如果我没有理解代码,请告诉我!

于 2009-10-23T09:36:19.397 回答