看模板类的时候发现有些地方使用到了友元,上课学的记不得了,赶紧温习下。。。
友元概念就不罗嗦了,使用也简单,就两种形式:
1.友元函数:friend ret-type classname::funname(....);
2.友元类:friend class classname;
唯一要注意的就是不管是友元函数还是友元类,定义友元关系前必须先声明
友元类其实还是有些故事要说的,一旦类继承起来友元关系还是有些小复杂的,下面简单说明:
C中声明A是其友元类,那么最基本的就是A可以使用C中的private方法或者对象。
图中可见,A是B的基类,C是D的基类。ABCD中就有如下关系:
1.B新增的方法不能访问C的私有成员
2.B从A继承而来的方法可以访问C的私有成员
3.A只能访问D中从C中继承而来的私有成员,D中新增的私有成员不能访问!
总结起来就是友元关系不可以继承,但对已有的方法来说访问权限不改变。如果改写基类的方法则访问权限改变
PS : 要特别谢谢有朋友留言纠正了我的错误,这次将测试用代码一并贴出
class C
{
friend class A;
private :
int numC;
};
class D : public C
{
private:
int numD;
};
class A
{
public:
//A是C的友元,可以访问C的私有成员
void getFromC()
{
C c;
c.numC = 100;
cout<<"getFromC in A : numC = "<<c.numC<<endl;
};
//A不是D的友元,不能访问D中新增的私有成员,但可以访问D从C中继承而来的私有成员
void getFromD()
{
D d;
d.numC = 23;
cout<<"getFromD in A : numC = "<<d.numC<<endl;
//d.numD = 24;
//cout<<"getFromD in A : numD = "<<d.numD<<endl;
}
};
class B :public A
{
public:
//友元关系不能继承,新增的方法不能访问C的私有成员
// int getNumB()
// {
// C c;
// c.numC = 100;
// return c.numC;
// }
//改写方法后对C访问权限改变,不能访问C的私有成员
// void getFromC()
// {
// C c;
// c.numC = 100;
// cout<<"getFromC in B : numC = "<<c.numC<<endl;
// }
};
int _tmain(int argc, _TCHAR* argv[])
{
A a;
a.getFromC();//输出——getFromC in A : numC = 100
a.getFromD();//输出——getFromD in A : numC = 23
B b;
b.getFromC();//输出——getFromC in A : numC = 100
//调用的还是A::getFromC
return 0;
}