最好不要把对象的定义和类的定义放在一起,这么做无异于把两种不同实体的定义混在了一条语句里,一会定义类,一会又定义变量,显然这是一种不被建议的行为。

类的定义最后要加上分号(:)

成员函数的声明必须放在类的内部,它的定义则既可以在类的内部也可以在类的外部,而作为接口组成部分的非成员函数,例如add、 read、和print等,他们的定义和声明都在外部

任何对类成员的直接访问都被看做this的隐式引用,也就是说,当isbn使用bookNo时,它隐式地使用this指向的成员,就像我们书写了this -> bookNo一样。this不能用作任何形参名和变量名。

std::string isbn() const { return this -> bookNo ;}

//因为this的目的总是指向这个对象,所以this是一个常量指针。紧跟在参数列表后面的const 表示this是一个指向常量的指针。像这样使用const的成员函数被称作常量成员函数(指明这个函数不会修改这个类的任何数据成员的值)。

可以把isbn()函数想象成如下形式

//伪代码,不能显示的定义this指针
std::string Sales_data::isbn(const Sales_data *const this) const { return this -> bookNo ;}

常量对象和常量对象的引用或指针都只能调用常量成员函数

编译器分两步处理类:首先编译成员的声明,然后才轮到成员函数体(如果有的话)。因此,成员函数体可以随意使用类中的其他成员而无需在意这些成员出现的次序。

像其它函数一样,当我们在类外部定义成员函数时,成员函数的定义必须与它的声明匹配。也就是说返回类型、参数列表和函数名都得与类内部的声明保持一致。如果成员被声明称常量成员函数,那么他的定义也必须在参数列表后表明指定const属性。同样,类外部定义的成员的名字必须包含它所属的类名:

double Sales_data::avg_price() const {        //Sales_data::加在函数名之前而非返回类型之前
if (units_sold)
return revenue / units_sold;
else
return 0;
}
Sales_data& Sales_data::combine(const Sales_data &rhs)
{
units_sold += rhs.units_sold; //把rhs的成员加到this对象的成员上
revenue += rhs.revenue;
return *this; //返回调用该函数的对象
}

当我的交易处理程序调用如下的函数时,

 total.combine(trans);

total的地址被绑定到隐式地this参数上,而rh绑定到了trans上。

这个函数一个值得关注的部分是它的返回类型和返回语句。一般来说,当我们定义的函数类似于某个内置运算符时,应该令该函数的行为尽量模仿这个运算符。内置的赋值运算符把他的左侧运算对象当成左值返回,因此为了与他保持一致性,combine函数必须返回引用类型。所以返回类型为Sales_data&。

int &refVal = ival;			//refVal 是ival的引用,是ival的另一个名字

既然Sales_data的数据成员是private的,我们的read、print、和add函数也就无法正常编译了,这是因为尽管这几个函数是类的接口的一部分,但他们不是类的成员,类可以允许其他类或者函数访问它的非公有成员,方法是令其它类或函数成为它的友元(friend),只需要增加一条以friend关键字开始的函数声明语句即可

istream &read(istream &is, Person &item)//编译无法通过,要在类内部添加函数友元声明
{
is >> item.strName >> item.strAddress;
return is;
}
friend istream &read(istream &, Person &);//友元声明

7.14构造函数

构造函数的名字和类名相同。和其他函数不一样的是,构造函数没有返回类型;构造函数也有一个(可能为空的)参数列表和一个(可能为空的)函数体。类可以包含多个构造函数,和其他重载函数差不多, 不同的构造函数之间必须在参数数量或参数类型上有所区别。此外,构造函数不能被声明成const的。

           默认构造函数又称之为合成的默认构造函数。

某些类不能依赖于合成的默认构造函数的情况:

1.只有当类没有声明任何构造函数时, 编译器才会自动地生成默认构造函数

2.如果类包含有内置类型或者复合类型的成员,则只有当这些成员全都被赋予了类内的初始值时,这个类才适用于合成的默认构造函数。(复合类型就是使用其他类型定义的类型,有三种复合类型,引用、指针、数组),内置类型就是(int、char、double、unsigned 等基本类型,若没有给这些成员初始值,默认值可能是未定义的)

3.如果类中包含一个其他类类型的成员且这个成员的类型没有默认构造函数,那么编译器就无法初始化该成员,也就无法生成默认的构造函数。对于这样的类来说,必须自定义默认构造函数。(classname() = default)

=default(默认构造函数)

构造函数初始值列表

Sales_data(const std::string &s) : bookNo(s) { }//未显示初始化的部分按默认初始化的方式初始化
等价于:
Sales_data(const std::string &s) : bookNo(s), units_sold(0), revenue(0) { }
Sales_data(const std::string &s, unsigned n, double p) :  //初始值列表
bookNo(s), units_sold(n), revenue(p * n) { }
等价于
Sales_data(const std::string &s, unsigned n, double p)
{
bookNo = s;
units_sold = n;
revenue = p * n;
}
二者有一些小小的区别,那就是前者是通过初始化的方式,后者是通过赋值的方式

构造函数最好使用类内初始值或初始值列表

重载运算符:

friend ostream &operator << (ostream & os, const Sales_data & rhs);
friend istream& operator >> (istream &is, Sales_data & rhs);

第七章 类(class)7.1 笔记的更多相关文章

  1. C#图解教程 第七章 类和继承

    类和继承 类继承访问继承的成员所有类都派生自object类屏蔽基类的成员基类访问使用基类的引用 虚方法和覆写方法覆写标记为override的方法覆盖其他成员类型 构造函数的执行 构造函数初始化语句类访 ...

  2. 《Java并发编程实战》第七章 取消与关闭 读书笔记

        Java没有提供不论什么机制来安全地(抢占式方法)终止线程,尽管Thread.stop和suspend等方法提供了这种机制,可是因为存在着一些严重的缺陷,因此应该避免使用. 但它提供了中断In ...

  3. 【C++】《C++ Primer 》第七章

    第七章 类 一.定义抽象数据类型 类背后的基本思想:数据抽象(data abstraction)和封装(encapsulation). 数据抽象是一种依赖于接口(interface)和实现(imple ...

  4. ArcGIS API for JavaScript 4.2学习笔记[24] 【IdentifyTask类】的使用(结合IdentifyParameters类)(第七章完结)

    好吧,我都要吐了. 接连三个例子都是类似的套路,使用某个查询参数类的实例,结合对应的Task类,对返回值进行取值.显示. 这个例子是Identify识别,使用了TileLayer这种图层,数据来自Se ...

  5. Android群英传笔记——第七章:Android动画机制和使用技巧

    Android群英传笔记--第七章:Android动画机制和使用技巧 想来,最 近忙的不可开交,都把看书给冷落了,还有好几本没有看完呢,速度得加快了 今天看了第七章,Android动画效果一直是人家中 ...

  6. 学习笔记(二)--->《Java 8编程官方参考教程(第9版).pdf》:第七章到九章学习笔记

    注:本文声明事项. 本博文整理者:刘军 本博文出自于: <Java8 编程官方参考教程>一书 声明:1:转载请标注出处.本文不得作为商业活动.若有违本之,则本人不负法律责任.违法者自负一切 ...

  7. [学习笔记—Objective-C]《Objective-C-基础教程 第2版》第二章~第七章

    在看完<Objective-C 程序设计 第6版>之后,看了一些关于iOS开发职位的面试题,发现自身基础非常是不牢,于是打算以查缺补漏的方式阅读还有一本关于Objective-C的基础书籍 ...

  8. Introduction to 3D Game Programming with DirectX 12 学习笔记之 --- 第七章:在Direct3D中绘制(二)

    原文:Introduction to 3D Game Programming with DirectX 12 学习笔记之 --- 第七章:在Direct3D中绘制(二) 代码工程地址: https:/ ...

  9. JVM学习笔记-第六章-类文件结构

    JVM学习笔记-第六章-类文件结构 6.3 Class类文件的结构 本章中,笔者只是通俗地将任意一个有效的类或接口锁应当满足的格式称为"Class文件格式",实际上它完全不需要以磁 ...

随机推荐

  1. jenkins自动化部署(tomcat+git)

    一.安装jenkins 1.安装jdk 查看可安装版本:yum search openjdk 安装:yum install -y java-1.8.0-openjdk java-1.8.0-openj ...

  2. 递归查询 start with connect by prior

    1.语法:start with 子节点ID='...' connect by prior 子节点ID = 父节点ID 含义:查询结果我所有的后代节点(包括我) 例子: select id,parent ...

  3. 关于 setw() 函数(C++)

    // about setw() #include <iostream> #include <iomanip> #include <cstring> using na ...

  4. PAT (Advanced Level) Practice 1036 Boys vs Girls (25 分)

    This time you are asked to tell the difference between the lowest grade of all the male students and ...

  5. Android View框架的draw机制

    概述 Android中View框架的工作机制中,主要有三个过程: 1.View树的测量(measure) Android View框架的measure机制 2.View树的布局(layout)Andr ...

  6. 关闭 APIPA

    遇到的问题:我在网卡2上设置了静态ip,可是出现了一个奇怪的ip地址169.254.*.*,如下图. 解决方法:关闭APIPA功能 按照下述的做法,自己在win7企业版上尝试了下,有效.不再出现169 ...

  7. php 公众号开发

    思考: 1,优先使用php扩展库的sdk,配合微信文档. 2,公众号开发比较简单,重在业务. 公众号关联与消息分发 <?php namespace app\wap\controller; use ...

  8. host文件无写权限时,怎么设置

    点击文件属性---安全---选择对应的用户---编辑属性---勾选需要的属性---应用---确定

  9. redis 列表类型list

    列表类型(list)1.插入 左侧插入 :lpush key value1 value2 value3... 右侧插入: lpush key value1 value2 value3... 在指定元素 ...

  10. Linux終端一行命令发送邮件

    近期由于经常需要给别人发送邮件,每次都要打开QQ邮箱觉得非常麻烦.想到Linux终端可以自定义命令,加上python可以实现邮件发送功能,于是自己写了一个终端send + 文件地址的命令. 首先贴上p ...