[C++] Six default member functions in class and object (middle) class (2) -- operator overloading -- take address and const take address operator overload

1 Introduction

In this article, we will start with the date class. For a date, how do we compare the size? It is OK to compare the year, month and day in turn, but can it be compared directly?

We can see that it is wrong to directly compare the size of two dates for the date class of the custom type, so we need to give special functions to the operator to realize the comparison of the custom type.

Some people here will think, then I can write a relatively small function, it is true, but this is not recommended. If we are writing a project with multiple people, the name of my comparative function function is different from the name that others think of. When we finally combine the code, we have to find the function name of a specific function, which will affect the efficiency of development. In order to avoid such a situation, C++ introduces the concept of operator overloading.

Let's take a look at how to achieve it.

2. Operator overloading

C++ introduces operator overloading to enhance the readability of the code. Operator overloading is a function with a special function name , and also has its return value type, function name, and parameter list. Its return value type and parameter list are similar to ordinary functions.
The function name is: the keyword operator followed by the operator symbol that needs to be overloaded.
Function prototype: return value type operator operator (parameter list)

Note:
1. New operators cannot be created by connecting other symbols: such as operator@

2. An overloaded operator must have a custom type parameter

3. The meaning of the operator used for built-in types cannot be changed, for example: the built-in integer + cannot change its meaning

4. When overloaded as a class member function, its formal parameters seem to be 1 less than the number of operands, because the first parameter of the member function is the hidden this

5. The number of operands of an operator cannot be changed. An operator has several operands, so there are several parameters when overloading

6、.*          ::         sizeof           ?:            .

Note that the above 5 operators cannot be overloaded.

Here we write the overload of <:

If it is written as a global function, the member variables in the Date class cannot be accessed. There are several solutions:

1. Change the member variable to shared , which is not safe;

2. Use friends , which will destroy the package;

3. Write a getXXX interface (like to use in Java) , which is too troublesome, as many member variables need to be written;

4. Put the overloaded function in the class , and the member variables in the class can be accessed, which is the most suitable.

Let's rewrite the following and write it into the class:

After modification:

class Date
{
public:
	Date(int year = 1, int month = 1, int day = 1)
	{
		_year = year;
		_month = month;
		_day = day;
	}

	//拷贝构造
	Date(const Date& d)// 拷贝构造对d不做改变,因此加上const防止违法使用
	{				   //并且对于引用来说,这也是权限的缩小,因此加const会更优
		_year = d._year;
		_month = d._month;
		_day = d._day;
	}

	void Print()
	{
		cout << _year << "/" << _month << "/" << _day << endl;
	}

	~Date()
	{
		_year = 0;
		_month = 0;
		_day = 0;
	}

	// d1 < d2 等同于 d1.operator<(d2),这里比较的顺序是不能交换的
	bool operator<(const Date& d)// 这里省略了第一个参数this
	{
		if (_year < d._year)
		{
			return true;
		}
		else if (_year == d._year && _month < d._month)
		{
			return true;
		}
		else if (_year = d._year && _month < d._month && _day < d._day)
		{
			return true;
		}
		else
		{
			return false;
		}

	}

private:
	int _year;
	int _month;
	int _day;
};

int main()
{
	Date d1(2003, 1, 1);
	Date d2(2023, 8, 2);
	cout << (d1 < d2) << endl;
	cout << (d1.operator<(d2)) << endl;

    return 0;
}

operation result:

We can see that is correct.

Here we are very detailed. The parameters use references, which can reduce copying and waste of space.

3. Address and const address operator overloading

These two default member functions generally do not need to be redefined, and the compiler will generate them by default.

class Date
{
public :
    Date* operator&()
    {
    return this ;
    }

    const Date* operator&()const
    {
    return this ;
    }

private :
    int _year ; // 年
    int _month ; // 月
    int _day ; // 日
};

These two operators generally do not need to be overloaded, just use the default address-taking overload generated by the compiler. Only in special cases, overloading is required, such as wanting others to obtain the specified content!

Guess you like

Origin blog.csdn.net/Ljy_cx_21_4_3/article/details/132102037