1.什么是模板?
泛型编程是指独立与任何类型的方式编写代码。泛型编程和面向对象编程,都依赖与某种形式的多态。面向对象编程的多态性在运行时应用于存在继承关系的类,一段代码可以可以忽略基类和派生类之间的差异。在泛型编程中,编写的代码可以用作多种类型的对象。面向对象编程所依赖的多态性称为运行时多态性,泛型编程所依赖的多态性称为编译时多态性或静态的多态性。
1)C++提供两种模板机制:函数模板、类模板
2)类属 —— 类型参数化,又称参数模板
使得程序(算法)可以从逻辑功能上抽象,把被处理的对象(数据)类型作为参数传递。
总结:
- 模板把函数或类要处理的数据类型参数化,表现为参数的多态性,称为类属。
- 模板用于表达逻辑结构相同,但具体数据元素类型不同的数据对象的通用行为。
2.函数模板
//函数模板声明
template <类型形式参数表>
类型 函数名(形式参数表)
{
语句序列
}
3.函数模板实现机制?
编译器并不是把函数模板处理成能够处理任意类的函数
编译器从函数模板通过具体类型产生不同的函数
编译器会对函数模板进行两次编译:
在声明的地方对模板代码本身进行编译;在调用的地方对参数替换后的代码进行编译。
4.类模板
//类模板由模板说明和类说明构成
template <类型形式参数表>
类声明
//例如
template<typename Type>
class TClass
{
//TClass的成员函数
private:
Type DataMember;
};
5.类模板的优点?
(1)可用来创建动态增长和减小的数据结构 (2)它是类型无关的,因此具有很高的可复用性。 (3)它在编译时而不是运行时检查数据类型,保证了类型安全 (4)它是平台无关的,可移植性 (5)可用于基本数据类型
6.实现自己的vector
myvector.h
#ifndef MYVECTOR_H
#define MYVECTOR_H
#include <iostream>
using namespace std;
template <typename T>
class MyVector
{
friend ostream& operator<< <T>(ostream &out, const MyVector<T>& obj);
public:
MyVector(int size = 0);
MyVector(const MyVector& obj);
~MyVector();
public:
int getLen()
{
return m_len;
}
T& operator[] (int index);
MyVector& operator=(const MyVector& obj);
protected:
T *m_space;
int m_len;
};
#endif
myvector.cpp
#include <iostream>
#include "MyVector.h"
using namespace std;
//注意:这边与声明时不同
template <typename T>
ostream& operator<<(ostream &out, const MyVector<T>& obj)
{
for (int i = 0; i < obj.m_len; i++)
{
out << obj.m_space[i] << " ";
}
out << endl;
return out;
}
template <typename T>
MyVector<T>::MyVector(int size)
{
m_space = new T[size];
m_len = size;
}
template <typename T>
MyVector<T>::MyVector(const MyVector& obj)
{
m_len = obj.m_len;
m_space = new T[m_len];
for (int i = 0; i < m_len; i++)
{
m_space[i] = obj.m_space[i];
}
}
template <typename T>
MyVector<T>::~MyVector()
{
if (m_space != NULL)
{
delete[] m_space;
m_space = NULL;
m_len = 0;
}
}
template <typename T>
T& MyVector<T>::operator[] (int index)
{
return m_space[index];
}
template <typename T>
MyVector<T>& MyVector<T>::operator=(const MyVector<T>& obj)
{
if (m_space != NULL)
{
delete[] m_space;
m_space = NULL;
m_len = 0;
}
m_len = obj.m_len;
m_space = new T[m_space];
for (int i = 0; i < m_len; i++)
{
m_space[i] = obj.m_space[i];
}
return *this;
}