打开APP
userphoto
未登录

开通VIP,畅享免费电子书等14项超值服

开通VIP
类模板中的友元声明和定义

普通友元:FooBar的成员和fcn函数可以访问Bar类的任意实例的private成员和protected成员

 

模板友元类FooBar

[c-sharp] view plaincopy
  1. #include <iostream>  
  2. using namespace std;  
  3.   
  4. template <class Type> class Bar  
  5. {  
  6.     friend class FooBar;  
  7.     Type pri;  
  8. };  
  9.   
  10. class FooBar  
  11. {  
  12.       public:  
  13.              template<typename T> void foofcn(const Bar<T>& b);   
  14.              //{cout<<b.pri<<endl;}//内部定义   
  15. };  
  16.   
  17. template<typename T>  
  18. void FooBar::foofcn(const Bar<T>& b)  
  19. {cout<<b.pri<<endl;}  
  20. int main(void)  
  21. {  
  22.     Bar<int> bi;  
  23.     Bar<float> bf;  
  24.     FooBar fb;  
  25.       
  26.     fb.foofcn(bi);  
  27.     fb.foofcn(bf);  
  28.       
  29.     system("pause");  
  30.     return 0;  
  31. }  

 

 

模板友元函数fcn

[c-sharp] view plaincopy
  1. #include <iostream>  
  2. using namespace std;  
  3.   
  4. template<class Type> class Bar  
  5. {  
  6.     friend void fcn(const Bar& b) { cout<<b.pri<<endl;}//效果同下   
  7.     //friend void fcn(const Bar<Type>& b) { cout<<b.pri<<endl;}  
  8.     Type pri;  
  9. };  
  10. //在类外部定义不能用 const Bar& b形式   
  11. //void fcn(const Bar& b)  
  12. //{ cout<<b.pri<<endl;}  
  13. int main(void)  
  14. {  
  15.     Bar<int>  bi;  
  16.     Bar<float>bf;  
  17.       
  18.     fcn(bi);  
  19.     fcn(bf);  
  20.     system("pause");  
  21. }  

 

 

一般模板友元关系:FooBar的任意实例都可以访问Bar的任意实例的私有成员。fcn函数相同

 

模板友元类FooBar

  1. #include <iostream>  
  2. using namespace std;  
  3.   
  4. template<class Type> class Bar  
  5. {  
  6.     template<class T> friend class FooBar;  
  7.     Type pri;  
  8. };  
  9.   
  10. template<typename T> class FooBar  
  11. {  
  12.     public:  
  13.            template<class U> void foofcn(const Bar<U>& b)  
  14.            { cout<<b.pri<<endl;}  
  15. };  
  16.   
  17. //在外面定义   
  18. /*template <class T> template<typename U> 
  19. void FooBar<T>::foofcn(const Bar<U>& b) 
  20. {cout<<b.pri<<endl;} */  
  21. int main(void)  
  22. {  
  23.     Bar<int> bi;  
  24.     Bar<float> bf;  
  25.     FooBar<int> fbi;  
  26.     FooBar<float> fbf;  
  27.       
  28.     fbi.foofcn(bi);  
  29.     fbi.foofcn(bf);  
  30.       
  31.     fbf.foofcn(bi);  
  32.     fbf.foofcn(bf);  
  33.       
  34.     system("pause");  
  35.     return 0;  
  36. }  

 

模板友元函数fcn

  1. #include <iostream>  
  2. using namespace std;  
  3.   
  4. template<typename Type> class Bar  
  5. {  
  6.     template<class T> friend void fcn(const Bar<T>& b) ;  
  7.     Type pri;  
  8. };  
  9.   
  10. template<typename T>   
  11. void fcn(const Bar<T>& b)  
  12.  {cout<<b.pri<<endl;}  
  13. int main(void)  
  14. {  
  15.     Bar<int>  bi;  
  16.     Bar<float>bf;  
  17.       
  18.     fcn(bi);  
  19.     fcn(bf);  
  20.     system("pause");  
  21. }  

 

函数定义在模板内部会导致重复定义

  1. #include <iostream>  
  2. using namespace std;  
  3.   
  4. template<typename Type> class Bar  
  5. {  
  6.     template<class T> friend void fcn(const Bar<T>& b) {cout<<b.pri<<endl;}   
  7.     Type pri;  
  8. };  
  9.   
  10. int main(void)  
  11. {  
  12.     Bar<int>  bi;  
  13.     //Bar<float>bf;  
  14.       
  15.     fcn(bi);  
  16.     //fcn(bf);  
  17.     system("pause");  
  18. }  

 

 

3.特定的模板友元关系:Bar实例只与有相同模板实参的FooBar版本是友元

 

3.1

模板友元类FooBar

  1. #include <iostream>  
  2. using namespace std;  
  3.   
  4. //需要前置声明 ,编译器将友元声明当作类的声明   
  5. template<class T> class FooBar;  
  6. template<class Type> class Bar  
  7. {  
  8.     friend class FooBar<Type>;  
  9.     Type pri;  
  10. };  
  11.   
  12. template<class T> class FooBar  
  13. {  
  14.     public:  
  15.            void foofcn(const Bar<T>& b);// {cout<<b.pri<<endl;}//在内部定义   
  16. };  
  17.   
  18. template<class T>  
  19. void FooBar<T>:: foofcn(const Bar<T>& b)  
  20. {cout<<b.pri<<endl;}  
  21.   
  22. int main(void)  
  23. {  
  24.     Bar<int> bi;  
  25.     Bar<float> bf;  
  26.     FooBar<int> fbi;  
  27.     FooBar<float> fbf;  
  28.       
  29.     fbi.foofcn(bi);  
  30.     //fbi.foofcn(bf);//error  
  31.       
  32.     //fbf.foofcn(bi);//error  
  33.     fbf.foofcn(bf);  
  34.       
  35.     system("pause");  
  36.     return 0;  
  37. }  

 

模板友元函数fcn

  1. #include <iostream>  
  2. using namespace std;  
  3. template<class T> class Bar;  
  4. template<class T> void fcn (const Bar<T>&);//需要前置声明   
  5. template<typename Type> class Bar  
  6. {  
  7.     //friend void fcn<Type>(const Bar<Type>& b);//模板特化   
  8.     friend void fcn<>(const Bar<Type>& b);//两种声明均可   
  9.     Type pri;  
  10. };  
  11.   
  12. template<class T>   
  13. void fcn (const Bar<T>& b)  
  14. {cout<<b.pri<<endl;}  
  15. int main(void)  
  16. {  
  17.     Bar<int>  bi;  
  18.     Bar<float>bf;  
  19.       
  20.     //fcn<float>(bi);//函数模板的类型可以和形参的模板类型不一致   
  21.     fcn<int>(bi);  
  22.     fcn(bi);  
  23.     fcn(bf);  
  24.     fcn<float>(bf);  
  25.     //fcn<int>(bf);  
  26.     system("pause");  
  27. }  

 

另一种写法,在模板类内部定义,调用fcn需要显示指定模板实参

  1. #include <iostream>  
  2. using namespace std;  
  3.   
  4. template<typename Type> class Bar  
  5. {  
  6.     template<class T> friend void fcn(const Bar<Type>& b) {cout<<b.pri<<endl;}   
  7.     Type pri;  
  8. };  
  9. int main(void)  
  10. {  
  11.     Bar<int>  bi;  
  12.     Bar<float>bf;  
  13.       
  14.     fcn<float>(bi);//函数模板的类型可以和形参的模板类型不一致   
  15.     fcn<int>(bi);  
  16.     //fcn(bf);//error//调用时要显示指定函数模板类型  
  17.     fcn<int>(bf);  
  18.     system("pause");  
  19. }  

 

 

3.2特定实例

 

模板友元类FooBar

  1. #include <iostream>  
  2. using namespace std;  
  3.   
  4. //需要前置声明   
  5. template<class T> class FooBar;  
  6.   
  7. template<class Type> class Bar  
  8. {  
  9.     friend class FooBar<float>;  
  10.     Type pri;  
  11. };  
  12.   
  13. template<typename T> class FooBar  
  14. {  
  15.     public:  
  16.            //foofcn(const Bar<T>& b)只能访问Bar的对应类型,不能访问所有类型   
  17.            //void foofcn(const Bar<T>& b) {cout<<b.pri<<endl;}  
  18.            template<class U> void foofcn(const Bar<U>& b) {cout<<b.pri<<endl;}  
  19. };  
  20. int main(void)  
  21. {  
  22.     Bar<int> bi;  
  23.     Bar<float> bf;  
  24.     FooBar<int> fbi;  
  25.     FooBar<float> fbf;  
  26.           
  27.     //fbi.foofcn(bi);  
  28.     //fbi.foofcn(bf);//error  
  29.       
  30.     fbf.foofcn(bi);//如果定义为foofcn(const Bar<T>& b),则fbf没访问bi私有变量的权限   
  31.     fbf.foofcn(bf);  
  32.       
  33.     system("pause");  
  34.     return 0;  
  35. }  

 

模板友元函数fcn

  1. #include <iostream>  
  2. using namespace std;  
  3. template<class T> class Bar;  
  4. template<class T> void fcn (const Bar<T>&);//需要前置声明   
  5. template<typename Type> class Bar  
  6. {  
  7.     friend void fcn<float>(const Bar<float>& b);  
  8.     Type pri;  
  9. };  
  10.   
  11. template<class T>   
  12. void fcn (const Bar<T>& b)  
  13. {cout<<b.pri<<endl;}  
  14. int main(void)  
  15. {  
  16.     Bar<int>  bi;  
  17.     Bar<float>bf;  
  18.       
  19.     //fcn<float>(bi);//函数模板的类型可以和形参的模板类型不一致   
  20.     //fcn<int>(bi);  
  21.     //fcn(bi);  
  22.     fcn(bf);//只接受Bar<float>实参   
  23.     fcn<float>(bf);  
  24.     //fcn<int>(bf);  
  25.     system("pause");  
  26. }  

 

可以将fcn定义为非模板

  1. #include <iostream>  
  2. using namespace std;  
  3.   
  4. template<typename Type> class Bar  
  5. {  
  6.     friend void fcn(const Bar<float>& b);  
  7.     Type pri;  
  8. };  
  9.   
  10.   
  11. void fcn (const Bar<float>& b)  
  12. {cout<<b.pri<<endl;}  
  13. int main(void)  
  14. {  
  15.     Bar<int>  bi;  
  16.     Bar<float>bf;  
  17.       
  18.     //fcn(bi);  
  19.     fcn(bf);//只接受Bar<float>实参   
  20.     //fcn<float>(bf);//fcn不是模板类函数   
  21.     system("pause");  
  22. }  

 

非类型形参的模板友元

 

模板友元类FooBar

  1. #include <iostream>  
  2. using namespace std;  
  3.   
  4. template<int hi> class Bar  
  5. {  
  6.     private:  
  7.             friend class FooBar;  
  8.             int pri;  
  9.     public:  
  10.             Bar():pri(hi) {}  
  11. };  
  12.   
  13. class FooBar  
  14. {  
  15.       public:  
  16.             template<int hi> void foofcn(const Bar<hi>& b) { cout<<b.pri<<endl;}  
  17. };  
  18.   
  19. int main(void)  
  20. {  
  21.     Bar<34> b;  
  22.     Bar<21> b1;  
  23.     FooBar fb;  
  24.       
  25.     fb.foofcn(b);  
  26.     fb.foofcn(b1);  
  27.     system("pause");  
  28.     return 0;  
  29. }  

 

模板友元函数fcn

  1. #include <iostream>  
  2. using namespace std;  
  3.   
  4. template<int hi> class Bar  
  5. {  
  6.     private:  
  7.             int pri;  
  8.     public:  
  9.             Bar():pri(hi) {}  
  10.             friend void fcn (const Bar<hi>& b) {cout<<b.pri<<endl;}  
  11. };  
  12.   
  13.   
  14.   
  15. int main(void)  
  16. {  
  17.     Bar<34> b;  
  18.     Bar<21> b1;  
  19.       
  20.     fcn(b);  
  21.     fcn(b1);  
  22.     system("pause");  
  23.     return 0;  
  24. }  

 

外部定义

  1. #include <iostream>  
  2. using namespace std;  
  3.   
  4. template<int hi> class Bar;  
  5. template<int a> void fcn(const Bar<a>& );  
  6. template<int hi> class Bar  
  7. {  
  8.     private:  
  9.             int pri;  
  10.     public:  
  11.             Bar():pri(hi) {}  
  12.             friend void fcn<> (const Bar<hi>& b);//定义在外部需要特化声明   
  13. };  
  14.   
  15. template<int hi>  
  16. void fcn(const Bar<hi>& b)  
  17. {cout<<b.pri<<endl;}  
  18.   
  19. int main(void)  
  20. {  
  21.     Bar<34> b;  
  22.     Bar<21> b1;  
  23.       
  24.     fcn(b);  
  25.     fcn(b1);  
  26.     system("pause");  
  27.     return 0;  
  28. }  

 

 

函数定义在类内部,每次实例化都会生成相应的版本,所以有时会导致重复定义的错误,但有些友元只能定义在模板的内部

本站仅提供存储服务,所有内容均由用户发布,如发现有害或侵权内容,请点击举报
打开APP,阅读全文并永久保存 查看更多类似文章
猜你喜欢
类似文章
【热】打开小程序,算一算2024你的财运
c – 制作boost :: interprocess共享内存对象的非共享副本
腾讯代码安全指南-C,C 安全指南
C++之virtual functions(虚函数)实现细节及相关概念 - Benjami...
C++实现两个栈实现一个队列和两个队列实现一个栈
C++的学习感想
超简略哈希表的实现
更多类似文章 >>
生活服务
热点新闻
分享 收藏 导长图 关注 下载文章
绑定账号成功
后续可登录账号畅享VIP特权!
如果VIP功能使用有故障,
可点击这里联系客服!

联系客服