一般情况下,一个类的成员数据只能被自身的成员函数所访问,不允许被外界对象或者函数所调用,但友元(frend)机制允许一个类将对其非公有成员的访问权授予指定的函数或者类。友元只能出现在类定义的内部,但可出现在类中的任何地方。通常一般将友元放到类定义的开头的开头和结尾。
友元一般有:友元函数 友元类和友元成员函数
1.友元函数
友元函数虽然不是某一类的成员函数但能够访问类的所有成员函数。该类授予了成员函数的访问权。
#include <iostream>
using namespace std;
class A{
public:
friend void setValue(int x, A &a);
private:
int data;
};
inline void A::setValue(int x, A &a){
a.data = x;
}
int main(){
class A a;
setValue(5,a);
return 0;
}
2.友元类
友元类的所有成员函数为另一个类的友元函数,可以访问另一个类的private 和 protect 的成员数据,当另一个类可以读写另一个类的私有成员时,可将该类声明为另一个类的友元类。例如下列代码的class C 为class A的友元类, C中的所有成员函数可以访问A的私有成员。
注意:
1.友元关系不可以被继承。
2.友元的关系是单向的,class C是class A的友元类但是A 不一定是C的友元类
3. 友元关系不具有传递性。若类B是类A的友元,类C是B的友元,类C不一定是类A的友元
#include <iostream>
using namespace std;
class A{
public:
friend class C;
private:
int data;
};
class C{
public:
void setValue(int x, A &a);
};
inline C::setValue(int x, A &a){
a.data = x;
}
int main(){
class A a;
class C c;
c.setValue(5,a);
}
3.友元成员函数
使类B中的成员函数成为类A的友元函数,这样类B的该成员函数就可以访问类A的所有成员了。
当用到友元成员函数时,需注意友元声明和友元定义之间的相互依赖,在该例子中,类B必须先定义,否则类A就不能将一个B的函数指定为友元。然而,只有在定义了类A之后,才能定义类B的该成员函数。更一般的讲,必须先定义包含成员函数的类,才能将成员函数设为友元。另一方面,不必预先声明类和非成员函数来将它们设为友元。
#include <iostream>
using namespace std;
class A; //当用到友元成员函数时,需注意友元声明与友元定义之间的互相依赖。这是类A的声明
class B{
public:
void setValue(int x, A &a); //该函数是类A的友元函数
};
class A{
public :
friend void B::setValue(int x, A &a); //该函数是友元成员函数的声明
private:
int data;
};
void B::setValue(int x, A &a){ //只有在定义类A后才能定义该函数,毕竟,它被设为友元是为了访问类A的成员
a.data = x;
}
int main(){
class A a;
class B b;
b.setValue(5,a);
}