C++学习笔记(17)——简析类模板

在《函数探幽》一文中总结了函数模板的相关的知识。我们大概知道模板提供了泛型编程的便利,也即我们可以用通用的类型来定义表征一系列类型,比如函数的形参。对于类,我们也可以设计一种通用的类型的类来实现代码的重用。本文将总结类模板的相关知识。

1.定义类模板

与模板函数类似,模板类也要以下面的代码开头:

template <class T>

这与函数模板的功能一样,也即声明T为一种通用类型。当然,这里的class并不是说后面的T必须为一个类,class可以换为typename。这里我们设计一个复数类。复数类的实部和虚部可以是整型和浮点型数据,因此模板可以很好的满足应用需求。

可以将类的成员变量和成员函数都声明为模板接口。比如Complex的实部和虚部,以及它重载四则运算的函数接口。但注意,在接口的是西安时(方法定义时)要在每个函数前面都要添加template <class T>,且要在类的作用域标识符前添加<T>.同时,不能将模板成员函数放在独立的实现文件中,所以通常我们把他们和类的声明一起写在头文件中。其中,若函数的实现是以内联函数的形式出现,则不必再函数前重复添加template <class T>。

2.使用模板类

与模板函数一样,再具体使用模板类时需进行实例化。也即使用具体的类型来替换泛型名。如:

Complex<int> iComplex(1,2);

Complex<float> fComplex(3.5,2.2);

其实际过程时用int或float替换类定义中所有的T。就如函数模板,类的模板也可以隐式实例化,显式实例化和显式具体化,相关的内容请参考函数探幽中的总结。

3.模板类与友元

我们想为Complex重载<<运算符以打印复数,鉴于之前的知识,我们知道需要通过友元来重载<<运算符。自然的想法是在类中添加声明:

friend std::ostream & operator<<(std::ostream & os, const Complex & c);//复数打印

具体定义为:

template <class T>

std::ostream & operator<<(std::ostream & os, const Complex<T> & c)

{

   os << c.a << "+" << c.b <<"i";

   return os;

}

如果你尝试这么做了,但是发现编译报错了。问题在于并没有完成具体化工作。我们需要修改的工作只需要在友元函数的声明处添加template <class T>模板头,也即将友元函数声明为函数模板,这样在具体化过程中即每个函数的具体化都是每个具体化的友元。这被称作模板类的非约束友元函数。

四、源码

#ifndef TEMPLATE_H
#define TEMPLATE_H

#include <iostream>

template <class T>
class Complex
{

private:
	T a;	//实部
	T b;	//虚部

public:
	//构造函数
	Complex(T a = 0, T b = 0);
	//接口函数
	T Real(){return a;};	//内联函数不必用template <class T>
	T Imag(){return b;};	//内联函数不必用template <class T>
	Complex  operator+(Complex &c);	//运算符重载

	//友元重载<<
	template <class T> friend std::ostream & operator<<(std::ostream & os, const Complex & c);//复数打印
};


//构造函数 需要有模板头
template <class T>
Complex<T>::Complex(T a, T b)
{
	this->a = a;
	this->b = b;
}

//运算符重载
template <class T>
Complex<T> Complex<T>::operator+(Complex<T> &c)
{
	Complex<T> tmp(this->a+c.a, this->b+c.b);
	return tmp;
}

//显示 重载<<  注意也需使用模板头
template <class T>
std::ostream & operator<<(std::ostream & os, const Complex<T> & c)
{
	os << c.a << "+" << c.b <<"i";
	return os; 
}

#endif

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

bjtuwayne

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值