C++ C++;can';无法从父级访问子属性

C++ C++;can';无法从父级访问子属性,c++,inheritance,C++,Inheritance,有人能解释一下为什么驱动程序初始化()方法无法打印在child中重写的名称属性吗 #include <iostream> #include <string> class Driver { public: std::string name = "Unknown"; void init() { std::cout << name << std::endl; } }; // need public here

有人能解释一下为什么
驱动程序
初始化()
方法无法打印在child中重写的
名称
属性吗

#include <iostream>
#include <string>

class Driver {
public:
    std::string name = "Unknown";

    void init() {
        std::cout << name << std::endl;
    }
};

// need public here to inherit init()
class SpecificDriver : public Driver {
public:
    std::string name = "Specific";

};

int main() {
    Driver d;
    SpecificDriver sd;

    // this gives Unknown Unknown =/
    d.init();
    sd.init();
}
应该是:

Unknown
Specific

你没有完全按照自己的想法去做。在驱动程序中声明变量“name”,在SpecificDriver中声明变量“name”。调用基类驱动程序中定义的
init()
时,该驱动程序只能访问其自己的
name
字段,其值为“未知”

相反,应该使用构造函数初始化“name”变量

像这样:

class Driver {
public:
    std::string name;

    Driver():name("Unknown"){} //default
    Driver(std::string value):name(value){}

    void init() {
        std::cout << name << std::endl;
    }
};

// need public here to inherit init()
class SpecificDriver : public Driver {
public:
    SpecificDriver():Driver("Specific"){}
};

int main() {
    Driver d;
    SpecificDriver sd;

    d.init();
    sd.init();
}
类驱动程序{
公众:
std::字符串名;
驱动程序():名称(“未知”){}//默认值
驱动程序(std::字符串值):名称(值){}
void init(){

std::cout您并没有完全按照您认为的方式进行操作。您在驱动程序中声明了一个变量“name”,在SpecificDriver中声明了一个变量“name”。当您调用基类驱动程序中定义的
init()
时,该驱动程序只能访问其自己的
name
字段,其值为“unknown”

相反,应该使用构造函数初始化“name”变量

像这样:

class Driver {
public:
    std::string name;

    Driver():name("Unknown"){} //default
    Driver(std::string value):name(value){}

    void init() {
        std::cout << name << std::endl;
    }
};

// need public here to inherit init()
class SpecificDriver : public Driver {
public:
    SpecificDriver():Driver("Specific"){}
};

int main() {
    Driver d;
    SpecificDriver sd;

    d.init();
    sd.init();
}
类驱动程序{
公众:
std::字符串名;
驱动程序():名称(“未知”){}//默认值
驱动程序(std::字符串值):名称(值){}
void init(){

STD:C++中的CUT< P>,虚拟继承是Opt in,而不是隐式。 当你有了这个密码

class Driver {
public:
    std::string name = "Unknown";

    void init() {
        std::cout << name << std::endl;
    }
};

在C++中,虚拟继承是Opt in,而不是隐式。 当你有了这个密码

class Driver {
public:
    std::string name = "Unknown";

    void init() {
        std::cout << name << std::endl;
    }
};

可以通过访问子类的类成员

#包括
模板
类驱动程序{
公众:
void init(){

std::cout name可以通过访问子类的类成员

#包括
模板
类驱动程序{
公众:
void init(){


STD::CUT名称不象经典继承。所以答案是不可能在C++中从父级访问子属性/方法?因为它与方法相同,请看上面我在您的问题和下面的评论上对Chris BeckThis的回答不象经典继承。所以,答案是在C++中,不可能从父级访问子属性/方法吗?因为它与方法相同,请参阅上面的问题,下面是Chris BeckThanks的回答。这使得 >名称< /Cord>一种方法。是否可以使用<代码>虚拟调度< /代码> <代码>名称>代码>将其作为属性?我同意。这是我通常在这种情况下设计东西的方式,我提出的方法是对原始代码的最简单的修改,但决不是实现结果的最佳方式虚拟分派只适用于您无法定义的成员函数/方法如果是虚拟财产,则必须选择Chris Beck或我提出的方法。但不可能将two@AlexZywicki谢谢你的澄清。我会用方法,因为现在对我来说更简单了。对于来自Python的人来说,初始值设定项仍然有点神秘。当你说“初始值设定项”你是指构造函数?还是成员变量的内联初始化。如
std::string name=“value”
谢谢。这使得
name
成为一种方法。是否可以将
virtualdispatch
用于
name
而将其作为一个属性?我同意这种方法很可能是解决问题的最具伸缩性和最简单的方法。在这种情况下,我通常会这样设计东西,我提出的方法是si对原始代码进行了最简单的修订,但绝不是实现结果的最佳方式虚拟分派仅适用于成员函数/方法您不能将属性声明为虚拟,您必须选择Chris Beck或我提出的方法。但无法将two@AlexZywicki谢谢你的澄清,我很乐意为你效劳请使用方法,因为现在对我来说更简单。对于来自Python的人来说,初始化器仍然有点神秘。当你说“初始化器”时,你是指构造函数还是成员变量的内联初始化。如
std::string name=“value”
我将提出一个问题:属性的值在派生类中不同,或者init执行的操作在派生类中不同,这更重要吗?或者两者都不同?如果您只需要“name”的值要想有所不同,您可以使用我的方法,但是如果您需要在派生版本中初始化其他内容,您可以使用Chris BeckI提出的方法,需要属性值不同-只需要在调试模式下输出驱动程序的名称,并且所有调试代码都在父级
init()中
@AlexZywicki和可读性也很重要-我仍然无法阅读/理解带有初始值设定项的代码(目前正在阅读教程)。我将提出一个问题:属性的值在派生类中不同,或者init执行的操作在派生类中不同,这更重要吗?或者两者都不同?如果您只需要“name”的值要想有所不同,您可以使用我的方法,但是如果您需要在派生版本中初始化其他内容,您可以使用Chris BeckI提出的方法,需要属性值不同-只需要在调试模式下输出驱动程序的名称,并且所有调试代码都在父级
init()中
@AlexZywicki和可读性也很重要-我仍然无法阅读/理解带有初始值设定项的代码(目前正在阅读教程)。
#include <iostream>

template <typename Derived>
class Driver {
public:
    void init() {
        std::cout << static_cast<Derived*>(this)->name << std::endl;
        std::cout << Derived::value << std::endl;
    }
};

class SpecificDriver : public Driver<SpecificDriver> {
public:
    std::string name = "Specific";
    static constexpr char* value = "Another specific string";
};

int main() {
    SpecificDriver g;
    g.init();
}