《C++ Primer Plus》读书笔记 第14章 C++中的代码重用

本文详细介绍了C++中的代码重用技术,包括使用包含对象成员的类、私有继承、保护继承、用using重新定义访问权限、多重继承以及类模板。强调了包含在建立has-a关系时的普遍偏好,但也讨论了私有继承在访问保护成员和重定义虚函数时的优势。此外,解释了多重继承带来的问题和解决方案,如虚基类的使用。文章还探讨了类模板的使用,包括模板参数、隐式和显式实例化、模板类和友元以及模板别名的概念。
摘要由CSDN通过智能技术生成

第14章 C++中的代码重用

1.包含对象成员的类

包含其他类对象的类,即has-a关系。用于建立has-a关系的C++技术是组合(包含)

class Student
{
   
private:
	typedef std::valarray<double> ArrayDb;
	std::string name;
	ArrayDb scores;
	std::ostream & arr_out(std::ostream & os) const;
public:
	Student() : name(“Null Student”), scores(){
   }
	explicit Student(const std::string & s) : name(s), scores() {
   }
	explicit Student(int n) : name(“Nully”), scores(n) {
   }
	Student(const std::string & s, int n) : name(s), scores(n) {
   }
	Student(const std::string & s, const ArrayDb & a) : name(s), scores(a) {
   }
	Student(cconst char * str, const double * pd, int n) : name(str), scores(pd, n) {
   }
	~Student() {
   }
	double Average() const;
	const std::string & Name() const;
	double & operator[](int i);
	double operator[](int i) const;
	friend std::istream & operator>>(std::istream & is, Student & stu);
	friend std::istream & getline(std::istream & is, Student & stu);
	friend std::ostream & operator<<(std::ostream & os, const Student & stu);
};

使用公有继承时,类可以继承接口,可能还有实现(基类的纯虚函数提供接口,但不提供实现)。获得接口是is-a关系的组成部分。而使用组合,类可以获得实现,但不能获得接口。不继承接口是has-a关系的组成部分。

2.私有继承

C++还有另一种实现has-a关系的途径——私有继承使用私有继承,基类的公有成员和保护成员都将称为派生类的私有成员

包含将对象作为一个命名的成员对象添加到类中,而私有继承将对象作为一个未被命名的继承对象添加到类中。使用术语子对象来表示通过继承或包含添加的对象。

要进行私有继承,将使用关键字private而不是public来定义类(实际上,private是默认值,因此省略访问限定符也将导致私有继承):

class Student : private std::string, private std::valarray<double>
{
   
public:
	//...
};

使用多个基类的继承被称为多重继承

包含版本提供了两个被显式命名的对象成员,而私有继承提供了两个无名称的子对象成员。

隐式地继承组件而不是成员对象将影响代码的编写,因为不能使用name和scores来描述对象。新版本的构造函数将使用雷鸣而不是成员名来标识构造函数:

Student(const char * str, const double double * pd, int n) : std::string(str), ArrayDb(pd, n){
   }

在私有继承中使用类名和作用域解析运算符来调用基类的方法:

double Student::Average() const
{
   
	if (ArrayDb::Size() > 0)
		return ArrayDb::sum() / ArrayDb::size();
	else
		return 0;
}

在私有继承中,如果要使用基类对象本身,可以利用强制类型转换:

const string & Student::Name() const
{
   
	return (const string &) *this;
}

在私有继承中,如果要使用基类的友元函数,可以通过显式地转换为基类来调用正确的函数:

ostream & operator<<
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值