类的函数成员
2023年12月20日 2023年12月30日
成员名字声明和函数定义的处理
编译时先处理类成员名字的声明,再处理类函数成员的定义
在类外定义成员函数
需要在函数名之前给出类名,进入到类的作用域. 形参列表和函数体都在类的作用域之中
类的返回类型不在类的作用域中
1double Sales_data::avg_price() const 2{ 3 if (units_sold) 4 return revenue / units_sold; 5 else 6 return 0; 7}
隐式this
对于非静态成员函数,一定是通过类对象调用成员函数
函数的传参不包括this指针,但成员函数拥有名为this的参数,指向调用该成员函数的对象
this指针具有顶层const. 即, 不可以使this指向其他对象
1class Sales_data 2{ 3public: 4 string isbn() const { return bookNo; } 5 Sales_data combine(const Sales_data&); 6 double avg_price() const; 7 string bookNo; 8 unsigned units_sold = 0; 9 double revenue = 0.0; 10}; 11ostream &print(ostream&, const Sales_data&); 12istream &read(istream&, Sales_data&);
1Sales_data total; 2total.isbn(); // Sales_data::isbn(&total); this = &total;
1string Sales_data::isbn() const 2{ 3 return bookNo; // return this->bookNo; 4}
返回this所指对象
1Sales_data& Sales_data::combine(const Sales_data &rhs) 2{ 3 units_sold += rhs.units_sold; 4 revenue += rhs.revenue; 5 6 return *this; // 返回非常量对象;this指针的类型为Sales_data *const 7}
const函数
用来修改this的类型, 使之具有底层const. 即, 此时不可以通过this对对象执行写操作
回收了类对象的写权限
const函数与this指针
- this具有底层const
- 通过this返回的对象具有顶层const
const函数的定义和声明
均要在形参列表之后给出const关键字
-
隐式内联函数
1struct Sales_data 2{ 3 Sales_data &combine(const Sales_data &); // this指针的类型为Sales_data *const 4 string isbn() const { return bookNo; } // this指针的类型为const Sales_data *const 5 6private: 7 string bookNo; 8};
-
声明和定义处均给出const关键字
1struct Sales_data 2{ 3 double avg_price() const; 4private: 5 string bookNo; 6 unsigned units_sold = 0; 7 double revenue = 0.0; 8}; 9 10double Sales_data::avg_price() const 11{ 12 if (units_sold) 13 return revenue / units_sold; 14 else 15 return 0; 16}
如果类对象具有顶层const, 只能对其调用const成员函数
如果类对象不具有顶层const, 可以对其调用类的所有public接口
类的成员函数可基于const重载
1class Screen 2{ 3public: 4 typedef string::size_type pos; 5 Screen &set(char); 6 Screen &move(pos r, pos c); 7 8 Screen() = default; 9 10 Screen(pos ht, pos wd, char c = ' ') : height(ht), width(wd), contents(ht * wd, c) { } 11 12 const Screen &display(ostream &os) const { do_display(os); return *this; } 13 Screen &display(ostream &os) { do_display(os); return *this; } 14 15private: 16 pos cursor = 0; 17 pos height = 0, width = 0; 18 string contents; 19 void do_display(ostream &os) const { os << contents; } 20// 当一个成员调用另一个成员时,this指针在其中隐式地传递; 21// 由display的非常量版本调用do_display时,它的this指针将隐式地从指向非常量的指针转换成指向常量的指针 22// 避免在多处使用同样的代码 23// 本身就是内联函数,不会添加额外的运行时开销 24}; 25 26inline screen &screen::set(char c) 27{ 28 contents[cursor] = c; 29 return *this; 30} 31 32Screen myScreen(5, 3); 33const Screen blank(5, 3); 34 35myScreen.move(4, 0).set('#'); // move和set的返回值都是非常量引用 36blank.display(cout).set('#'); // 错误: blank是常量对象,匹配const Screen &display(ostream&) const;而set非const成员,调用失败
可在const函数中对可变数据成员执行写操作
内联函数
-
隐式内联函数
不使用关键字inline, 但在类内给出函数定义 -
在类外定义内联函数
需给出关键字inline在类内声明成员函数, 在类外定义成员函数; 声明和定义其中一处给出inline关键字即可
可以同时给出