天天看點

C++的二義性和虛基類C++的二義性和虛基類

C++的二義性和虛基類

一、二義性問題

1.在繼承時,基類之間、或基類與派生類之間發生成員同名時,将出現對成員通路的不确定性——同名二義性。

2.當派生類從多個基類派生,而這些基類又從同一個基類派生,則在通路此共同基類中的成員時,将産生另一種不确定性——路徑二義性。

二、同名二義性

同名隐藏規則——解決同名二義的方法

             1、當派生類與基類有同名成員時,派生類中的成員将屏蔽基類中的同名成員。

             2、若未特别指明,則通過派生類對象使用的都是派生類中的同名成員;

             3、如要通過派生類對象通路基類中被屏蔽的同名成員,應使用基類名限定(::)。

三、路徑二義性

虛基類規則-------解決路徑二義性的方法

             1、派生對象時使基類成為虛基類,可以解決路徑二義性的問題;

四、舉例說明

1、同名二義性

#include <iostream>
using namespace std;

class B0
{
public:
	B0(int b0)
	{
		m_b0 = b0;
		cout << "B0 construction" << endl;
	}

	void fun()
	{
		cout << "fun of BO" << endl;
	}
private:
	int m_b0;
};

class B1 : public B0
{
public:
	B1(int b0, int b1) : B0(b0)
	{
		m_b1 = b1;
		cout << "B1 construction" << endl;
	}

	void fun()
	{
		cout << "fun of B1" << endl;
	}	
private:
	int m_b1;
};

int main()
{
	B1 b(1, 2);
	b.fun();     //通路B1的fun()
	b.B0::fun();  //通路B0的fun()

	return 0;
}      

2、路徑二義性

#include <iostream>
using namespace std;

class B0
{
public:
	B0(int b0)
	{
		m_b0 = b0;
		cout << "B0 construction" << endl;
	}

	void fun()
	{
		cout << "fun of BO" << endl;
	}
private:
	int m_b0;
};

class B1 : virtual public B0
{
public:
	B1(int b0, int b1) : B0(b0)
	{
		m_b1 = b1;
		cout << "B1 construction" << endl;
	}

private:
	int m_b1;
};

class B2 : virtual public B0
{
public:
	B2(int b0, int b2) : B0(b0)
	{
		m_b2 = b2;
		cout << "B2 construction" << endl;
	}

private:
	int m_b2;
};

class D0 : public B1, public B2
{
public:
	D0(int b0, int b1, int b2, int d0) : B0(b0), B1(b0, b1), B2(b0, b2)
	{
		m_d0 = d0;
		cout << "D0 construction" << endl;
	}

	void fun()
	{
		cout << "fun of DO" << endl;
	}
private:
	int m_d0;
};

int main()
{
	D0 d(1, 2, 3, 4);
	d.fun(); //通路D0的fun()

	return 0;
}      

繼續閱讀