天天看點

【C++基礎之十】友元函數和友元類

1.概述

友元提供了一種 普通函數或者類成員函數 通路另一個類中的私有或保護成員 的機制。也就是說有兩種形式的友元:

(1)友元函數:普通函數對一個通路某個類中的私有或保護成員。

(2)友元類:類A中的成員函數通路類B中的私有或保護成員。

2.特性

優點:提高了程式的運作效率。

缺點:破壞了類的封裝性和資料的透明性。

3.實作

3.1.友元函數

3.1.1.聲明和定義

在類聲明的任何區域中聲明,而定義則在類的外部。

friend <類型><友元函數名>(<參數表>);
           

注意,友元函數隻是一個普通函數,并不是該類的類成員函數,它可以在任何地方調用,友元函數中通過對象名來通路該類的私有或保護成員。

3.1.2.示例

// TestFriend.cpp

#include "stdafx.h"

class A
{
public:
	A(int _a):a(_a){};

	friend int getA_a(A &_classA);//友元函數

private:
	int a;
};

int getA_a(A &_classA)
{
	return _classA.a;//通過對象名通路私有變量
}

int _tmain(int argc, _TCHAR* argv[])
{
	A _classA(3);
	std::cout<<getA_a(_classA);//友元函數隻是普通函數,可以在任意地方調用
	return 0;
}
           

3.2.友元類

3.2.1.聲明和定義

友元類的聲明在該類的聲明中,而實作在該類外。

friend class <友元類名>;
           

友元類的執行個體則在main函數中定義。

3.2.2.示例

// TestFriend.cpp

#include "stdafx.h"

class B
{
public:
	B(int _b):b(_b){};

	friend class C;//聲明友元類C

private:
	int b;
};

class C//實作友元類C
{
public:
	int getB_b(B _classB){
		return _classB.b;//通路友元類B的私有成員
	};
};


int _tmain(int argc, _TCHAR* argv[])
{
	B _classB(3);
	C _classC;//定義友元類執行個體
	std::cout<<_classC.getB_b(_classB);
	return 0;
}
           

4.注意

4.1.友元關系沒有繼承性

假如類B是類A的友元,類C繼承于類A,那麼友元類B是沒辦法直接通路類C的私有或保護成員。

4.2.友元關系沒有傳遞性

加入類B是類A的友元,類C是類B的友元,那麼友元類C是沒辦法直接通路類A的私有或保護成員,也就是不存在“友元的友元”這種關系。

繼續閱讀