读书笔记:C++ primer 5th edition--chapter7.类


part1.基本用法
1.const 成员函数示例代码
string Sales_data::isbn (const Sales_data *const this){ return this->isbn;}
2.成员函数返回值
当我们定义的函数类似于内置运算符时,应该令该函数的行为尽量模仿这个运算符。内置运算符把它的左侧运算对象当成左值返回。因此成员函数也应返回:return *this;//解引用this指针以获得执行该函数的对象
3.构造函数
      Sales_data() = default;
     c++11用 =default来要求编译器合成默认构造函数。
     若=default和声明一起出现在类的内部,则默认构造函数为内联。

4.类外部定义构造函数
Sales_data::Sales_data(std::iostream &is ){
     read(is, *this );//使用*this将对象作为整体访问(引用)
}
5.拷贝,赋值和析构
当类需要分配类的对象之外的资源时,合成版本通常失效。但是如果类包含vector,或者string成员,那么合成版本的函数也能work。
6.private,public:访问说明符
一个类可以包含0个到多个访问说明符,有效范围直到出现下一个访问说明符或者结尾。
7.友元函数,一般最好在类定义开始或结束前的位置集中声明友元。
8.定义在类内部的成员函数是自动inline的。可在类外用inline修饰函数的定义。
9.可变数据成员,即使在一个const成员函数内也能被改变。mutable size_t access_ctr;
10.const成员函数返回*this,返回类型是常量引用。此时无法适用于一个序列的操作中。
myScreen.move(4, 0).set(‘ * ‘)  //ok
myScreen.display(cout).set(‘ * ‘) //如果display返回常量引用则调用set将引发错误
可以用基于const的重载,
定义名为do_display的私有成员,负责实际打印工作。再定义常量和非常量版本的display公有成员。
如果display的非常量版本调用do_display时,它的this指针讲隐世地从指向飞常量的指针转换成指向常量的指针。do_display之后,display函数各自返回解引用this所得的对象。
优点:避免多出使用相同代码,便于添加调试信息,不会增加额外开销。
11.类类型
类型比较:即使两个类的成员列表完全一致,它们也是不同的类。
不完全类型:仅声明类而不定义,叫做前向声明,此时是一个不完全类型。使用场景有限,如定义指向这种类型的指针和引用,也可以声明以此为参数或者返回类型的函数
因为只有当类全部完成后类才算被定义,所以一个类的成员类型不能是该类自己。然后类名出现则算声明过了,因此可以包含指向它自身类型的引用或者指针。just like link_node
12.友元函数:尽管重载函数名字相同,他们仍然是不同的函数。所以只对声明了友元的有效。

part2.类的作用域
1.编译器处理完类中的全部声明后才会处理成员函数的定义。因此成员函数体可以使用类中定义的任何名字。
2.成员定义中的普通块作用域的名字查找
1)首先在成员函数内查找
2)找不到则在类内继续查找,类所有成员会被考虑
3)还找不到则在成员函数定义之前的作用域内查找

part3.构造函数再探
1.如果成员是const,引用,或者属于某种未提供默认构造函数的类类型,我们必须通过构造函数初始值列表为这些成员提供初值。这是唯一的机会。而且效率上比赋值要高。
2.c11定义了委托构造函数:一个委托构造函数使用它所属的类的其他构造函数执行它自己的初始化过程。
3.隐式地类类型转换
如果构造函数只接受一个实参,此时的构造函数被称为转换构造函数。它定义了一条从构造函数的参数类型向类类型隐式转换的规则。但这种转换只允许一步。如果是:“sss” > string > class 则不work
可以被explicit抑制。

part4.静态成员
1.需求场景:类需要它的一些成员与类本身直接相关,而不是与类的各个对象保持关联。因此对象中不包含任何与静态数据成员有关的数据。类似的,静态成员函数不与对象绑定,不含this指针。静态成员函数不能声明成const的。
2.必须在类的外部定义和初始化静态成员。只能定义一次。如何保证??
3.类的静态成员不该在类内部初始化。
1)虽然可以通过constexpr实现。另外,即使在内部被初始化了,也该在类外定义一下该成员。
2)关于常量表达式constexpr:
A.编译期间就可以求值的,比如字面值,全局变量,sizeof返回的结果。
B.可以用于enum,switch,数组长度等场景
C.uage:
constexpr  int  Inc( int  i) {
     return  i + 1;
}
 
constexpr  int  a = Inc(1); // ok
constexpr  int  b = Inc(cin.get()); // !error
constexpr  int  c = a * 2 + 1; // ok

D.优点:编译器可以在编译期对constexpr的代码进行优化,比如直接替换成最终结果。相比宏来说,没有额外开销。更安全可靠。
E. const并未区分出编译期常量和运行期常量, constexpr限定在了编译期常量。
传入的参数如果不能在编译时期计算出来,那么constexpr修饰的函数就和普通函数一样了。因此能用就用。
而检测constexpr函数是否产生编译时期值的方法是利用std::array需要编译期常值才能编译通过的小技巧。
4.区别:1)可以是不完全类型 2)可以作为默认实参 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值