2017-02-19 28 views
2

請看下面的例子:如何根據派生類的這個指針找到成員函數?

struct B1 { 
    void f() { 
     this->g(); 
     std::cout << this << std::endl; 
    } 
    void g() { 
     std::cout << "B1::g" << std::endl; 
    } 
}; 

struct B2 { 
    void f() { 
     this->g(); 
     std::cout << this << std::endl; 
    } 
    void g() { 
     std::cout << "B2::g" << std::endl; 
    } 
}; 

struct C: B1, B2 { 
    void f() { 
     B1::f(); 
     B2::f(); 
     std::cout << this << std::endl; 
    } 
    void g() { 
     std::cout << "C::g" << std::endl; 
    } 
}; 

int main() { 
    C c; 
    c.f(); 
    return 0; 
} 

對於我來說,輸出是:

B1::g 
0x7fffa11436b7 
B2::g 
0x7fffa11436b7 
0x7fffa11436b7 

讓我們專注於B2::f。從輸出中看到,在B2::f,this內部指向類型爲C的對象的開頭。那麼,this->g()如何正確解析爲B2::g()

+0

還有什麼會解決什麼?除了'B2 :: g()'之外,你會期望它是* other嗎?雖然實際調用的機制不是由語言標準來定義的,但決議肯定是這樣。無論如何,將它編譯爲asm,你可能會發現'this-> g()'只不過是簡單地推一下'this'(顯然寄存器優化是潛在的),而直接調用'B :: g )'。畢竟,'g()'不是虛擬的。 – WhozCraig

+0

指針值誤導你。將數據成員添加到三個結構中的每一個,然後重試。 –

回答

0

這裏沒有功能是虛擬的。所以你你打電話g會員功能從B1::f你叫根據定義B1::g。事情的確會去不同,如果g是虛擬的,因爲那時所有f功能會叫C::g(只是嘗試在所有3層結構與virtual void g()更換void g()

相關問題