C++中友元的实例详解
|
由于这将调用Tv的一个方法,所以编译器此时已经看到了Tv类的声明,这样才能知道Tv有哪些方法,但正如看到的,该声明位于Remote声明的后面。这种问题的解决方法是:使用Remote声明中只包含方法声明,并将实际的定义放到Tv类之后。 所以最终应该这样:
class Tv; //前向声明
class Remote {...} //如要用到Tv 只能是方法声明
class Tv{...}
//接着写Remote的定义
这里通过方法定义中使用 inline关键字,仍然可以使方法称为内联方法
#ifndef TV_H_
#define TV_H_
class Tv; //前向声明
class Remote {
public:
enum {
off,on //开关
};
enum
{
MinVal,MaxVal = 20 //音量
};
enum {
Antena,Cable //使用的天线、还是电缆
};
enum
{
TV,DVD //工作模式
};
private:
int mode; // 控制 TV 或 DVD
public:
Remote(int m = TV) :mode(m) {}
//用到了Tv 只能是声明
bool volup(Tv & t);
bool voldown(Tv & t);
void onoff(Tv & t);
void chanup(Tv & t);
void chandown(Tv & t);
void set_chan(Tv &t,int c);
void set_mode(Tv &t);
void set_input(Tv &t);
};
class Tv
{
public:
friend void Remote::set_chan(Tv & t,int c); //友元成员函数
enum {
off,DVD //工作模式
};
Tv(int s = off,input(TV) {}
void onoff() { state = (state == on) ? off : on; }
bool ison()const { return state == on; }
bool volup(); //增大声音
bool voldown(); //减小声音
void chanup(); //频道 +
void chandown();//频道 -
void set_mode() { mode = (mode == Antena) ? Cable : Antena; }
void set_input() { input = (input == TV) ? DVD : TV; }
void settings()const; //显示所有设置
private:
int state; // 开或者 关
int volume; // 音量
int maxchannel; //最大
int channel; //当前频道
int mode; // 广播还是 电缆
int input; //Tv 或者 DVD
};
inline bool Remote::volup(Tv & t) { return t.volup(); }
inline bool Remote::voldown(Tv & t) { return t.voldown(); }
inline void Remote::onoff(Tv & t) { return t.onoff(); }
inline void Remote::chanup(Tv & t) { return t.chanup(); }
inline void Remote::chandown(Tv & t) { return t.chandown(); }
inline void Remote::set_chan(Tv &t,int c) { t.channel = c; }
inline void Remote::set_mode(Tv &t) { return t.set_mode(); }
inline void Remote::set_input(Tv &t) { return t.set_input(); }
#endif // TV_H_
测试结果不变。 *另外:也可一个将内联函数放在tv.cpp中,但必须去掉inline关键字,这样函数的连接性将成为外部的。 三、其他友元关系 1、上面的代码表示的是Remote是Tv的友元。但我们有时也会用到2个类互相友元。即Remote是Tv的友元,同时 Tv又是Remote的友元 他们定义与下面类似:
class Remote
class Tv
{
friend clas Remote
public:
void buzz(Remote & r) ;
...
}
class Remote
{
friend class Tv;
public:
void Bool volup(Tv & t){t.volup();}
...
}
inline void Tv::buzz(Remote & r)
{
...
}
由于Remote的声明位于Tv声明的后面,所以可以在类的定义Remote::volup(),但Tv::buzz()方法必须在Tv声明的外部定义,使其位于Remote声明的外面。如果不希望buzz()是内联的,则应在一个单独的方法定义文件中定义它。 2、共同的友元。 需要使用友元的另一种情况是,函数需要访问两个类的私有数据。它可以是一个类的友元,同时是另一个类的友元。示例如下:
class Analyzer;
class Probe
{
friend void sync (Analyzer & a,const Probe & p) ;
friend void sync (Probe & p,const Analyzer & a);
...
};
class Analyzer
{
friend void sync (Analyzer & a,const Analyzer & a);
}
inline void sync (Analyzer & a,const Probe & p)
{
...
}
inline void sync (Probe & p,const Analyzer & a)
{
...
}
如有疑问请留言或者到本站社区交流讨论,感谢阅读,希望能帮助到大家,谢谢大家对本站的支持! (编辑:清远站长网) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |


