#include <iostream> using namespace std; class Base { public: int i; Base() { i = 9999; fun(); } virtual void fun() { cout<<"Base.fun()"<<endl; } }; class Derived : public Base { public: int i; Derived() { i = -1; } virtual void fun() { cout<<"Derived.fun()"<<endl; } }; int main(int argc, char *argv[]) { Base *b = new Derived(); cout<<(b->i)<<endl; b->fun(); }

java 代碼:
class Base { int i = 9999; public void fun() { System.out.println("Base.fun()"); } Base() { fun(); } } class Derived extends Base { int i = -1; Derived(){} public void fun() { System.out.println("Derived.fun()"); } } public class dev { public static void main(String argv[]) { Base b = new Derived(); System.out.println(b.i); b.fun(); } }

差異體現在第一行輸出;
這行是在Derived的構造函數中輸出的,Derived本身沒有構造函數,它只調用父類的構造函數,即Base的Base(), 並執行其中的 fun() 函數;
對於C++代碼,執行的是Base::fun();
對於Java代碼,執行的是Derived::fun();
為什么呢,在C++中調用基類的fun時,此時子類還沒有准備好,故執行的是基類的fun。
分析:區別原因在於編譯器,及其運行原理
C++ 代碼 經過編譯后 Base構造函數中的代碼為靜態,其中調用的其他函數地址也已經在編譯時 就已經確定, 故執行的是 Base::fun() 。(除了虛函數是動態聯編其他的都是靜態代碼)
Java 代碼,為動態聯編, 各個函數在編譯時已經形成虛擬機機器指令代碼, 但是具體的函數調用卻是動態的, 因為是派生類調用父類的構造函數,所以這里的 fun() 函數被認為是 派生類 derived 中的。
