多重继承方法解析:C ++与Python

时间:2015-07-01 00:41:22

标签: python c++ multiple-inheritance

我看到C ++和Python如何处理钻石继承场景的行为非常不同。

对于以下两个代码片段,逻辑是相同的但输出是不同的。我不明白为什么。如果有人能提供一些见解,我真的很感激。

Python打印出“B B”

class A(object):
    def foo(self):
        print 'A'

class B(A):
    def foo(self):
        print 'B'
    def bar(self):
        self.foo()

class C(A):
    def foo(self):
        print 'C'
    def bar(self):
        self.foo()

class D(B, C):
    def bar(self):
        B.bar(self)
        C.bar(self)

D().bar()

但C ++打印出“B C”

struct A
{   
    virtual void foo() {
        cout << "A" << endl;
    }   
};  

struct B : public A
{   
    virtual void foo() {
        cout << "B" << endl;
    }   

    virtual void bar() { this->foo(); }
};  

struct C : public A
{   
    virtual void foo() {
        cout << "C" << endl;
    }   

    virtual void bar() { this->foo(); }
};  

struct D : public B, public C
{   
    virtual void bar() {
        B::bar();
        C::bar();
    }   
};  

int main()
{   
    D().bar();
} 

当我在C ++中为上面的每个cout << typeid(*this).name() << endl;方法添加行bar()时,这就是打印出来的内容:

B 0x7fff803d9b70
C 0x7fff803d9b78
D 0x7fff803d9b70

似乎BD共享相同的地址,但C位于不同的vtable中。

修改

正如回复@JoranBeasley所建议的,我尝试了以下对python代码的检查:

D.foo == B.foo
D.foo == C.foo
D.foo is B.foo
D.foo is C.foo

Python 2.7打印出True False False False

Python 3.4打印出True False True False

似乎B.fooD.foo在python 2和3中都是相同的方法,但是python 2会生成副本,而python 3则不会。

1 个答案:

答案 0 :(得分:3)

我只能解释python位......

C.bar(self)

将您创建的D实例传递为self

所以当它调用self.foo()时,与self.foo()内部D.bar内部self所说的情况没有什么不同(即B.foo仍然是静态相同的事情)

因为继承是从右到左C.foo阴影D.foo is B.foo # should print True D.foo is C.foo # should print false

C.foo(self) #prints C as expected

你可以粗略地打电话

super()

这与Python多重继承方法解析顺序无关,因为它是用class D(C,B): ... 调用处理的......相反,你试图显式调用你的父类方法,而不是让python来解决它们对你暗示

至于为什么它与C ++不同,因为它是两种独立的语言,以不同的方式实现了继承和多重继承...

如评论中所述,您可以将D的定义更改为

D().foo()

然后C将打印@Scripts.Render("bundles/js/app") if (User.IsInRole("Admin") { Scripts.Render("bundles/js/admin") }