1. 程式人生 > >友元類與友元函式的繼承與傳遞問題

友元類與友元函式的繼承與傳遞問題

    C++ Primer中有如下描述:友元關係不能被繼承,基類的友元對派生類沒有特殊的訪問許可權。

    然而通過實踐發現,VS編譯器並沒有安裝上述描述來處理,下面的規則與上述描述相悖,卻符合VS編譯器的處理規則。

    注:有待通過g++編譯器來驗證。

1 友元類的繼承問題

1.1一個友元類的派生類,可以通過其基類介面去訪問設定其基類為友元類的類的私有成員,也就是說一個類的友元類的派生類,某種意義上還是其友元類,這句話有點繞,上程式碼就清晰了

示例程式碼:

#include <iostream> 
using namespace   std; 
class B; 
class A 
{ 
	int a; 
public: 
	A(int x=0) { a=x; } 
	friend class B; 
}; 
class B 
{ 
	int b; 
public: 
	void fun(A& ob){ cout << ob.a << endl;} 
}; 

class C:public B
{ 
public: 
	//void fun2(A& ob){ cout <<ob.a <<endl;}   //派生類新加的函式卻不能訪問A,此句會報錯
}; 

void   main() 
{ 
	A a(55); 
	C c; 
	c.fun(a); //C是B的派生類   通過基類B的函式fun仍然可以訪問 
} 
1.2.一個派生類的基類的友元類仍然是它的友元類

示例程式碼如下

#include <iostream> 
using namespace std; 
class B; 
class A 
{ 
	int a; 
public: 
	A(int x=0){ a=x; } 
	friend class B; 
}; 

class C:public A     //通過繼承,A的友員類B成了派生類C的友員類 
{ 
public: 
	C(int x):A(x){} 
};

class B 
{
public: 
	void fun(A& ob) { cout <<ob.a << endl; } 
	void fun2(C& ob) { cout << ob.a << endl; } 
}; 

void main() 
{ 
	C c(55); 
	B b; 
	b.fun(c); 
	b.fun2(c);
} 

2 友元函式的繼承問題

基類的友元函式仍然是派生類的友元函式

示例程式碼:

#include <iostream> 
using namespace   std;  
class B;
class A 
{ 
	int a; 
public: 
	A(int x=0) { a=x; } 
	friend void fun(B&); //若註釋掉此句則無法通過編譯
	virtual ~A(){} //用作基類的類皆新增一個虛解構函式是一個好習慣,無論解構函式是否真的需要
}; 

class B: public A
{
public:
	B(int x): A(x) {}
};

void fun(B& o)
{
	cout << o.a << endl;
}

void   main() 
{ 
	//A a(55);
	B b(66);
	//fun(a);
	fun(b);
} 

3 友元類的傳遞問題

一個友元類B的友元類,對將B設定為友元類的類沒有特殊的訪問許可權

示例程式碼如下:

#include <iostream> 
using namespace   std; 
class A 
{ 
	int a; 
public: 
	A(int x=0) { a=x; } 
	friend class B; 
}; 

class B 
{ 
public: 
	void fun(A& ob) { cout << ob.a << endl; }
	friend class C;
};

class C
{
public:
	void fun(A& ob) { cout << ob.a << endl; } //此句無法通過編譯
};

void   main() 
{ } 

4 友元函式的傳遞問題

一個友元類的友元函式對設定這個類為友元類的類沒有特殊訪問許可權

示例程式碼如下:

#include <iostream> 
using namespace   std; 
class A 
{ 
	int a; 
public: 
	A(int x=0) { a=x; } 
	friend class B; 
}; 

class B 
{ 
public: 
	void fun(A& ob){ cout << ob.a << endl;} 
	friend void fun2(A& ob);
}; 

void fun2(A& ob)
{	cout << ob.a << endl; //此句無法通過編譯 
}

void   main() 
{ }