C++黑马程序员——P124-126. 赋值 关系运算符重载;函数调用运算符重载

  • P124. 类和对象——C++运算符重载——赋值运算符重载
  • P125. 类和对象——C++运算符重载——关系运算符重载
  • P126. 类和对象——C++运算符重载——函数调用运算符重载
  • P124. 赋值运算符重载

 C++编译器至少给一个类添加4个函数:

1. 默认构造函数(无参,函数体为空)

2. 默认析构函数(无参,函数体为空)

3. 默认拷贝构造函数,对属性进行值拷贝

4. 赋值运算符 operator=,对属性进行值拷贝

 

如果类中有属性指向堆区,做赋值操作时也会出现深浅拷贝问题。

 1 //赋值运算符重载
 2 class Person
 3 {
 4 public:
 5     Person(int age)
 6     {
 7         //将年龄数据开辟到堆区
 8         m_Age = new int(age);
 9     }
10     ~Person()
11     {
12         if (m_Age != NULL)
13         {
14             delete m_Age;
15             m_Age = NULL;
16         }
17     }
18 
19     //重载赋值运算符
20     Person& operator=(Person& p)
21     {
22         //编译器提供的浅拷贝:
23         //m_Age = p.m_Age;
24         //应该先判断本身是否有属性(m_Age)在堆区,如果有,先释放干净,然后再深拷贝
25         if (m_Age != NULL)
26         {
27             delete m_Age;
28             m_Age = NULL;
29         }
30         m_Age = new int(*p.m_Age); //深拷贝;*是解引用
31         //返回对象本身
32         return *this;    //返回值为本身是为了连等,例如 a=b=c;如果返回值是void,就调用不了连等(因为b=c时返回void,那么a就不能=void类型)
33     }
34 
35     int* m_Age;
36 };
37 
38 void test01()
39 {
40     Person p1(18);
41     Person p2(20);
42     Person p3(30);
43     p3 = p2 = p1;    //赋值操作;编译器提供的赋值操作为浅拷贝(p2和p1的m_Age都会指向同一块内存空间),析构时会重复释放,造成错误
44     cout << "p1的年龄为:" << *p1.m_Age << endl;
45     cout << "p2的年龄为:" << *p2.m_Age << endl;
46     cout << "p3的年龄为:" << *p3.m_Age << endl;
47 }
48 
49 int main()
50 {
51     test01();
52     return 0;
53 }

运行结果:

  

 

  • P125. 关系运算符重载

作用:重载关系运算符,可以让两个自定义类型对象进行对比操作

 1 //重载关系运算符
 2 class Person
 3 {
 4 public:
 5     Person(string name, int age)
 6     {
 7         m_Name = name;
 8         m_Age = age;
 9     }
10     string m_Name;
11     int m_Age;
12 };
13 
14 //==运算符重载
15 bool operator==(Person& p1, Person& p2)
16 {
17     if ((p1.m_Name == p2.m_Name) && (p1.m_Age == p2.m_Age))
18     {
19         return 1;
20     }
21     else
22     {
23         return 0;
24     }
25 }
26 
27 void test01()
28 {
29     Person p1("Tom", 18);
30     Person p2("Tom", 18);
31     if (p1 == p2)
32     {
33         cout << "p1 和 p2 相等" << endl;
34     }
35 }
36 
37 int main()
38 {
39     test01();
40     return 0;
41 }

运行结果:

  

 

  • P126. 函数调用运算符重载

函数调用运算符:()

● 函数调用运算符()也可以重载

● 由于重载后使用的方式非常像函数的调用,因此称为仿函数

● 仿函数没有固定写法,非常灵活

 1 //函数调用运算符()重载
 2 //打印输出类
 3 class MyPrint
 4 {
 5 public:
 6     //重载函数调用运算符
 7     void operator()(string test)
 8     {
 9         cout << test << endl;
10     }
11 };
12 
13 void test01()
14 {
15     MyPrint m1;
16     //调用 重载函数调用运算符
17     m1("hello world"); //由于使用起来非常类似函数调用,因此称为仿函数
18 }
19 
20 //仿函数非常灵活,没有固定写法
21 //加法类
22 class MyAdd
23 {
24 public:
25     int operator()(int num1, int num2)
26     {
27         return num1 + num2;
28     }
29 };
30 
31 void test02()
32 {
33     MyAdd add1;
34     int a1 = add1(1, 2);
35     cout << "a1 = " << a1 << endl;
36     //匿名函数对象;匿名对象特点:当前行执行完后,会被立即释放
37     cout << "MyAdd()(3, 4) = " << MyAdd()(3, 4) << endl; //类名+小括号+参数列表
38 }
39 
40 int main()
41 {
42     test01();
43     test02();
44     return 0;
45 }

运行结果:

  

(〃>_<;〃)(〃>_<;〃)(〃>_<;〃)

posted @ 2023-02-22 14:56  我会变强的  阅读(15)  评论(0编辑  收藏  举报