这是基本的c++,但是我想说的是python实际上看起来更简单。假设:
class Base
{
public:
virtual ~Base() = default;
virtual std::string type() const { return "base"; };
};
class Derived1 : public Base
{
public:
virtual std::string type() const { return "dervied1"; };
};
class Derived2 : public Base
{
public:
virtual std::string type() const { return "dervied2"; };
};
我发现我自己有其他类型的函数:
void process(Base& derived_from_base)
{
};
Q1:我怎么知道我作为输入,我是否应该调用type(),然后向下投射,问题是我认为type()将总是给出"base"?
这太烦人了。之后,我必须将输入向下大小写转换为正确的派生类。我只是想知道python是否在后台做这些,我确定我比python快吗?Q3:我真的可以用模板代替虚函数/继承和所有类型转换吗?(在某处听到的,不确定)。非常感谢。
Q1:我如何知道我正在作为输入的内容?
A1:保留完整类型,而不是将其擦除到基类。例如:代替
void process(Base& base) {
if (base.type() == "derived1") process_derived1(static_cast<Derived1&>(base));
else process_anything_else(base);
}
int main() {
std::unique_ptr<Base> base = std::make_unique<Derived1>();
process(*base);
}
使用void process(Derived1& derived1) { process_derived1(derived1); }
void process(auto& t) { process_anything_else(t); }
int main() {
Derived derived1;
process(derived1);
}
Q2:我只是想知道python是否在后台做这些,我确定我比python更快吗?
A2: Python有这样的代码:
int main() {
Object derived1; // a hash map
derived1["__type__"] = "Derived1";
}
使用A1的方法,由于静态分派,您比任何东西都快(假设程序中的其他一切都不差):多亏了模板,重载解析在编译时发生,因此不需要花费任何成本。
Q3:它是真的,我可以取代虚拟函数/继承和所有使用模板的类型转换?(在某处听到的,不确定)
A3:通过适当的设计,您可以在大多数情况下做到这一点,例如参见A1。然而,有些东西会强制动态链接:操作系统API、游戏插件等。在这种情况下,考虑本地化笨拙的边界部分,这样大多数代码可以像往常一样编写。
虚拟函数/继承
注意:没有虚函数的继承是非常好的,并且是零成本的(就其本身而言),例如参见CRTP。