1.設有類A,和類B兩個類,假定類A的聲明在類B之前(類的聲明總會有先後之分)
2.類A與類B,各自具有一個private權限的func函數。
一、類A,類B的聲明如下(定義在在同一個源檔案中):
#include <iostream>
class A{
private:
void func()
{
std::cout << "A::func()" << std::endl;
}
};
class B{
private:
void func()
{
std::cout << "B::func()" << std::endl;
}
};
int main()
{
system("pause");
return 0;
}
執行結果:
二、若類A,有一個成員函數call_func_of_B(B &b)想要調用類B的private成員函數func(),為了
解決這個問題可将call_func_of_B(B &b)函數聲明為類B的友元函數,代碼書寫如下:
#include <iostream>
class B;//由于類B的定義在類A之後,是以用到類B的聲明時,使用前向聲明
class A{
private:
void func()
{
std::cout << "A::func()" << std::endl;
}
public:
void call_func_of_B(B &b);//可以使用類B定義指針,引用,對象,因為上文有前向聲明
};
class B{
private:
void func()
{
std::cout << "B::func()" << std::endl;
}
friend void A::call_func_of_B(B &b);//友元聲明将類A的成員函數聲明為類B的友元函數
};
//定義類A成員函數
void A::call_func_of_B(B &b)
{
b.func();
}
測試代碼:
int main(){
A a;
B b;
a.call_func_of_B(b);
system("pause");
return 0;
}
執行結果:
注意的問題:
1.不能将call_func_of_B()函數的定義放在它聲明的地方,代碼如下:
#include <iostream>
class B;//由于類B的定義在類A之後,是以用到類B的聲明時,使用前向聲明
class A{
private:
void func()
{
std::cout << "A::func()" << std::endl;
}
public:
void call_func_of_B(B &b)//可以使用類B定義指針,引用,對象,因為上文有前向聲明
{
//b.func();
//前向聲明能力有限,對于類B的細節,隻有定義之後才能通路
}
};
2.也不能在聲明友元函數是對call_func_of_B()函數進行定義
class B{
private:
void func()
{
std::cout << "B::func()" << std::endl;
}
friend void A::call_func_of_B(B &b)//友元聲明将類A的成員函數聲明為類B的友元函數
{
//b.func();//C3060 不允許對使用限定名的友元函數進行定義
}
};
對于C3060編譯器錯誤,參見MSDN: http://msdn.microsoft.com/en-us/library/9h84hcy4(v=vs.90).aspx
三、由于類B的定義晚于類A的定義,若要使類B的成員通路類A的非public成員,需将類B設為類A的友元類
#include <iostream>
class B;//由于類B的定義在類A之後,是以用到類B的聲明時,使用前向聲明
class A{
private:
void func()
{
std::cout << "A::func()" << std::endl;
}
public:
void call_func_of_B(B &b);//可以使用類B定義指針,引用,對象,因為上文有前向聲明
friend class B;//此時若要用B的成員函數通路A的非public成員,隻能将類B設為類A的友元類
};
class B{
private:
void func()
{
std::cout << "B::func()" << std::endl;
}
public:
void call_func_of_A(A &a);
friend void A::call_func_of_B(B &b);//友元聲明将類A的成員函數聲明為類B的友元函數
};
void A::call_func_of_B(B &b)
{
b.func();
}
void B::call_func_of_A(A &a)
{
a.func();
}
int main()
{
A a;
B b;
a.call_func_of_B(b);
b.call_func_of_A(a);
system("pause");
return 0;
}
執行結果:
1.同樣,類B的成員函數可在類B中定義,也可在類B作用域外定義
class B{
private:
void func()
{
std::cout << "B::func()" << std::endl;
}
public:
void call_func_of_A(A &a)
{
a.func();
}
friend void A::call_func_of_B(B &b);//友元聲明将類A的成員函數聲明為類B的友元函數
};
以上代碼,可以執行成功!