现在的位置: 首页 > 综合 > 正文

thinking in c++ 读书笔记—友元函数的一个问题

2013年07月30日 ⁄ 综合 ⁄ 共 895字 ⁄ 字号 评论关闭
首先还是一个程序段:如下是两个类的声明.
struct x;
struct y
{
 void f(x *memx);
};
struct x{
 private :
  int i;
 public :
  void print();
  friend void y::f(x *memx );
};
 struct Y有一个成员函数f( ),它将修改X类型的对象。这里有一个难题,因为C + +的编译器要求在引用任一变量之前必须声明,所以struct Y必须在它的成员Y :: f(X*)被声明为struct X的一个友元之前声明,但Y :: f(X*)要被声明,struct X又必须先声明。
 解决的办法是:注意到Y :: f(X*)引用了一个X对象的地址。这一点很关键,因为编译器知道如何传递一个地址,这一地址大小是一定的,而不管被传递的对象类型大小。如果试图传递整个对象,编译器就必须知道X的全部定义以确定它的大小以及如何传递它,这就使程序员无
法声明一个类似于Y :: g(X) 的函数。通过传递X的地址,编译器允许程序员在声明Y :: f(X*)之前做一个不完全的类型指定。这一点是在struct X的声明时完成的,这儿仅仅是告诉编译器,有一个叫X的s t r u c t ,所以当它被引用时不会产生错误,只要程序员的引用不涉及名字以外的其他信息。
 这样,在struct X中,Y :: f(X*)就可以成功地声明为一个友元函数,如果程序员在编译器获得对Y的全部指定信息之前声明它,就会产生一条错误,这种安全措施保证了数据的一致性,
同时减少了错误的发生。
 经过我的试验,发现这里void f(x *memx)改成void f(x &memx)(引用)也是可以的,但是改成void f(x memx);却有一个warning.
 同样,如果程序改成下面的形式,把x,y的struct声明颠倒一下位置,如下:
struct y;
struct x{
 private :
  int i;
 public :
  void print();
  friend void y::f(x &memx );
};
struct y
{
 void f(x &memx);
};
结果仍然是错误的.第一句不完整的struct y声明不能在后面使用y::f()函数.

 

抱歉!评论已关闭.