//: C05:FriendScope.cpp #include <iostream> using namespace std; class Friendly { int i; public: Friendly(int theInt) { i = theInt; } friend void f(const Friendly&); // Needs global def. void g() { f(*this); } }; void h() { f(Friendly(1)); // Uses ADL } void f(const Friendly& fo) { // Definition of friend cout << fo.i << endl; } int main() { h(); // Prints 1 Friendly(2).g(); // Prints 2 } ///:~
Listado 6.36. C05/FriendScope.cpp
//: C05:FriendScope2.cpp #include <iostream> using namespace std; // Necessary forward declarations: template<class T> class Friendly; template<class T> void f(const Friendly<T>&); template<class T> class Friendly { T t; public: Friendly(const T& theT) : t(theT) {} friend void f<>(const Friendly<T>&); void g() { f(*this); } }; void h() { f(Friendly<int>(1)); } template<class T> void f(const Friendly<T>& fo) { cout << fo.t << endl; } int main() { h(); Friendly<int>(2).g(); } ///:~
Listado 6.37. C05/FriendScope2.cpp
//: C05:FriendScope3.cpp {-bor} // Microsoft: use the -Za (ANSI-compliant) option #include <iostream> using namespace std; template<class T> class Friendly { T t; public: Friendly(const T& theT) : t(theT) {} friend void f(const Friendly<T>& fo) { cout << fo.t << endl; } void g() { f(*this); } }; void h() { f(Friendly<int>(1)); } int main() { h(); Friendly<int>(2).g(); } ///:~
Listado 6.38. C05/FriendScope3.cpp
template<class T> class Box { T t; public: Box(const T& theT) : t(theT) {} };
//: C05:Box1.cpp // Defines template operators. #include <iostream> using namespace std; // Forward declarations template<class T> class Box; template<class T> Box<T> operator+(const Box<T>&, const Box<T>&); template<class T> ostream& operator<<(ostream&, const Box<T>&); template<class T> class Box { T t; public: Box(const T& theT) : t(theT) {} friend Box operator+<>(const Box<T>&, const Box<T>&); friend ostream& operator<< <>(ostream&, const Box<T>&); }; template<class T> Box<T> operator+(const Box<T>& b1, const Box<T>& b2) { return Box<T>(b1.t + b2.t); } template<class T> ostream& operator<<(ostream& os, const Box<T>& b) { return os << '[' << b.t << ']'; } int main() { Box<int> b1(1), b2(2); cout << b1 + b2 << endl; // [3] // cout << b1 + 2 << endl; // No implicit conversions! } ///:~
Listado 6.39. C05/Box1.cpp
//: C05:Box2.cpp // Defines non-template operators. #include <iostream> using namespace std; template<class T> class Box { T t; public: Box(const T& theT) : t(theT) {} friend Box<T> operator+(const Box<T>& b1, const Box<T>& b2) { return Box<T>(b1.t + b2.t); } friend ostream& operator<<(ostream& os, const Box<T>& b) { return os << '[' << b.t << ']'; } }; int main() { Box<int> b1(1), b2(2); cout << b1 + b2 << endl; // [3] cout << b1 + 2 << endl; // [3] } ///:~
Listado 6.40. C05/Box2.cpp
// Inside Friendly: friend void f<>(const Friendly<double>&);
// Inside Friendly: friend void g(int); // g(int) befriends all Friendlys
template<class T> class Friendly { template<class U> friend void f<>(const Friendly<U>&);