In depth analysis of friend functions and friend classes in c++

  • 2020-04-02 01:14:22
  • OfStack

The requirements of friend function and friend class:
Class has the characteristics of encapsulation and information hiding. Only a member function of a class can access a private member of the class. No other function in the program can access a private member. Non-member functions can access public members of a class, but if you define all data members as common, you break the hidden feature. In addition, you should see that in some cases, especially when some member functions are called multiple times, the efficiency of the program is affected due to the time cost of parameter passing, type checking, security checking, and so on.

In order to solve the above problems, a scheme of using friend elements is proposed. A friend is a normal function that is defined outside of a class, but it needs to be explained inside the class. To distinguish it from the member functions of the class, the keyword friend is used before the explanation. A friend is not a member function, but it can access private members in a class. Friends are used to make the program run more efficiently, but they break the encapsulation and concealment of the class, allowing non-member functions to access private members of the class.
A friend can be a function, which is called a friend function; A friend can also be a class, which is called a friend class.

A friend function
Friend functions feature nonmember functions that can access private members in a class. Friend function from the point of view of syntax, it is the same as the ordinary function, that is, in the definition and call the same as the ordinary function. Here is an example to illustrate the application of friend functions.


#include "iostream"
#include "cmath"
using namespace std;
class Point
{
private:
 double x,y;
public:
 Point(double xx, double yy) { x=xx; y=yy; }
 void Getxy();
 friend double Distance(Point &a, Point &b);  //Friend identifies it as a friend function, not a member function,
};
void Point::Getxy()
{
 cout<<"("<<x<<","<<y<<")"<<endl;
}
double Distance(Point &a, Point &b) 
{
 double dx = a.x - b.x;  //Private members in a class can be accessed
 double dy = a.y - b.y;
 return sqrt(dx*dx+dy*dy);
}
int main(void)
{
 Point p1(3.0, 4.0), p2(6.0, 8.0);
 p1.Getxy();    //Calling a member function
 p2.Getxy();
 double d = Distance(p1, p2);  //Call the friend function, is the same as the ordinary function call, do not call like a member function
 cout<<"The distance is "<<d<<endl;
 system("pause");
 return 0;
}

Description: The Point class in the program illustrates a friend function Distance(), which prefixes the friend keyword to indicate that it is not a member function but a friend function. It is defined in the same way as a normal function definition, but not in the same way as a member function definition, because it does not need to indicate which class it belongs to. However, it can refer to private members of a class, and the function bodies of a.x, b.x, a.y, and b.y are all private members of the class, which are referred to by objects. When calling a friend function, it is the same as a normal function call, do not call like a member function. In this case, p1.getxy () and p2.getxy () are calls to the member functions, to be represented by objects. Distance(p1, p2) is a call to the friend function, which is directly called without the need for object representation, and its parameters are objects.

Friends metaclass
In addition to the functions mentioned above, a friend can also be a class, that is, a class can be a friend of another class. When a class is a friend of another class, it means that all member functions of that class are friends of another class.
Note when using friend metaclass:
(1) friends cannot be inherited.
(2) the friendship relationship is one-way and not exchangeable. If class B is A friend of class A, class A is not necessarily A friend of class B, depending on whether there is A corresponding declaration in the class.
(3) the friend relationship is not transitive. If class B is the friend of class A, and class C is the friend of class B, class C is not necessarily the friend of class A, also depends on whether there is A corresponding declaration in the class
In C, A is declared as its friend metaclass, so the most basic thing is that A can use the private method or object in C.
So A is the base class of B, and C is the base class of D. ABCD has the following relationship:
1. The new method of B cannot access the private member of C
2. A method that B inherits from A can access A private member of C
3.A can only access private members inherited from C in D, and new private members in D cannot!

To sum up:
(1) friend relationships cannot be inherited, but the access rights for existing methods do not change.
(2) if the methods of the base class are overwritten, the access rights will be changed
(3) the friend relationship is not transitive
If class B is A friend of class A, and class C is A friend of class B, class C is not necessarily A friend of class A


Related articles: