C++ 模板的简易讲解

Posted S for N

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了C++ 模板的简易讲解相关的知识,希望对你有一定的参考价值。

模板的概念

模板(Template)指C++程序设计设计语言中采用类型作为参数的程序设计,支持通用程序设计。C++ 的标准库提供许多有用的函数大多结合了模板的观念,如STL以及IO Stream。模板是C++支持参数化多态的工具,使用模板可以使用户为类或者函数声明一种一般模式,使得类中的某些数据成员或者成员函数的参数、返回值取得任意类型。
模板的原理是什么:编译器根据调用的函数模板和类模板的类型实例化出对应的函数和类
简而言之一句话,模板就是让程序员写与类型无关的代码

模板分类(包含实例化)

模板分为函数模板和类模板两种,下面我将详细介绍两类模板

函数模板

首先为什么会有函数模板?

//如果我们想实现多种类型的Swap交换函数
void Swap(int& left, int& right) 
{
 	int temp = left;
 	left = right;
 	right = temp; 
 }
void Swap(double& left, double& right) 
{
	 double temp = left;
	 left = right;
	 right = temp; 
}
void Swap(char& left, char& right) 
{
	 char temp = left;
	 left = right;
	 right = temp; 
}
......

我们需要写多个swap函数,可是这些函数基本是重复的,那么我们能不能用一个通用的函数来实现呢?

//下面就是函数模板(template<class T>和template<typename T>这两种没什么区别,一般都喜欢使用class)
//template<class T>
template<typename T>  //这两种都行没区别  模板类型参数
void Swap(T& x1, T& x2)
{
	T x = x1;
	x1 = x2;
	x2 = x;
}

T就相当于一种不确定的类型,我们使用的时候根据传参不同编译器会实例化出不同的函数。
那么编译器根据我们传参的不同推演出模板参数的实际类型的行为,称之为隐式实例化

// 隐式实例化举例
int main()
{
	int a = 0, b = 0;
	Swap(a, b);

	double c = 1.11, d = 2.22;
	Swap(c, d);

	char e = 'a', f = 'b';
	Swap(e, f);

	return 0;
}

那么既然隐式实例化,肯定就会有显式实例化,什么时候我们需要用到显式实例化呢?
就是我们传的两个参数的类型是不同的,那么编译器没法推到出来,这个时候就需要我们自己给出类型。

//下面是举例
template<class T>
T Add(const T& left, const T& right) 
{
	return left + right;
}

int main()
{
	int a1 = 10, a2 = 20;
	double d1 = 10.0, d2 = 20.0;
	//隐式实例化(T的类型是编译器自己推导的)
	Add(a1, a2);
	Add(d1, d2);

	//这样编译器就没法自己推导了
	//Add(a1, d1);
	//那么有两种方式可以解决
	Add(a1, (int)d1);

	//显示实例化(指定T的类型)
	Add<int>(a1, d1);
	return 0;
}

类模板

类模板其实和函数模板大同小异
咱们可以直接来看一下类模板的格式

// 类模板格式
必须以关键字template开始,后面是尖括号括起来的模板参数,然后是类名
template<class T1, class T2, ..., class Tn>
class 类模板名
{
 // 类内成员定义
};
在类声明中,欲采用通用数据类型的数据成员、成员函数的参数或返回类型前面需要加上类型参数。
template<class T>
class Stack
{
public:
	Stack(size_t capacity = 10)
		: _pData(new T[capacity])
		, _size(0)
		, _capacity(capacity)
	{}

	// 使用析构函数演示:在类中声明,在类外定义。
	~Stack();

	void PushBack(const T& data);
	void PopBack();
		// ...

	size_t Size() 
	{ 
		return _size; 
	}

	T& operator[](size_t pos)
	{
		assert(pos < _size);
		return _pData[pos];
	}

private:
	T* _a;
	size_t _size;
	size_t _capacity;
};

int main()
{
	// Stack类名,Stack<int>才是类型
	Stack<int> s1;
	Stack<double> s2;
}

可以看到类模板实例化需要在类模板名字后跟<>,然后将实例化的类型放在<>中即可,类模板名字不是真正的类,而实例化的结果才是真正的类。
这就是c++模板的简易讲解。

以上是关于C++ 模板的简易讲解的主要内容,如果未能解决你的问题,请参考以下文章

简易前端模板引擎

C++入门篇之模板基础讲解

C++入门篇之模板基础讲解

poj3648:Wedding——题解(配2-SAT简易讲解)

用类的继承关系实现简易后台代码模板

VSCode自定义代码片段——.vue文件的模板