函数模板
相当于函数重载的进阶,类型参数化
数据的类型也可以通过参数传递 在函数定义时可以不指明具体的数据类型,当发生函数调用时,编译器根据传入的实参自行推断数据类型,相当于类型参数化
函数模板
建立一个通用函数,用到的数据类型(返回值、形参类型、局部变量类型)无需具体指定,用一个标识符来站位,等发生函数调用时再根据传入的实参来逆推出真正的类型 一旦定义类函数模板,就可以将类型参数 用于函数定义和函数声明,(将内置类型的地方,用类型参数来代替)
template 函数模板关键字 <> 占位符 typename T 声明具体的类型参数,类型参数是T template <typename T> 模板头,模板头中包含的类型参数可以用在函数定义的各个位置,包括返回值、形参列表和函数体
#include <iostream>
using namespace std;
template <typename T> T mmax(T a,T b);
template <typename T> void swap(T *a,T *b)
{
T temp=*a;
*a=*b;
*b=temp;
}
template <typename T>
T mmax(T a,T b)
{
if (a>=b)
return a;
else
return b;
}
int main()
{
int a=10,b=20;
swap(&a,&b);
cout<<a<<" "<<b<<endl;
char c='a',d='b';
swap(&c,&d);
cout<<c<<" "<<d<<endl;
bool e=false,f=true;
swap(&e,&f);
cout<<e<<" "<<f<<endl;
cout<<mmax(a,b)<<endl;
return 0;
}
类模板
类模板中定义的类型参数可以在类声明和类定义中
template<typename T1,typename T2>
class MyPoint
{
private:
T1 x;
T2 y;
public:
MyPoint(T1 x,T2 y);
void setx(T1 x);
T1 getx() const;
void sety(T2 y);
T2 gety() const;
MyPoint *print() const;
};
template<typename T1,typename T2>
MyPoint<T1,T2>::MyPoint(T1 x,T2 y)
{
this->x=x;
this->y=y;
}
template<typename T1,typename T2>
void MyPoint<T1,T2>::setx(T1 x)
{
this->x=x;
}
template<typename T1,typename T2>
void MyPoint<T1,T2>::sety(T2 y)
{
this->y=y;
}
template<typename T1,typename T2>
T1 MyPoint<T1,T2>::getx() const
{
return this->x;
}
template<typename T1,typename T2>
T2 MyPoint<T1,T2>::gety() const
{
return this->y;
}
template<typename T1,typename T2>
MyPoint<T1,T2>* MyPoint<T1,T2>::print() const
{
return new MyPoint(this->x,this->y);
}
int main()
{
MyPoint<int,int> p1(1,2);
MyPoint<float,float> p2(3.,4.);
MyPoint<int,char*> p3(5,"lisi");
MyPoint<int,int> *p4=new MyPoint<int,int>(6,7);
MyPoint<int,int> *point_ptr=p1.print();
cout<<point_ptr->getx()<<" "<<point_ptr->gety()<<endl;
MyPoint<float,float> *point_ptr2=p2.print();
cout<<point_ptr2->getx()<<" "<<point_ptr2->gety()<<endl;
delete point_ptr;
delete point_ptr2;
delete p4;
return 0;
}
例子2 !!!
#include <iostream>
using namespace std;
template <typename T>
class List
{
private:
int length;
T *ptr;
public:
List(int length);
List(List &arr);
~List();
void push_back(const T &v);
T size();
T & operator[](int idx);
};
template <typename T>
List<T>::List(int length)
{
this->length=length;
if (length==0)
{
this->ptr=NULL;
}
else
{
this->ptr=new T[this->length]();
}
}
template <typename T>
List<T>::List(List &arr)
{
if (!arr.ptr)
{
this->ptr==NULL;
this->length=0;
return ;
}
this->ptr=new T[arr.length];
memcpy(this->ptr,arr.ptr,sizeof(T)*arr.length);
this->length=arr.size;
}
template <typename T>
List<T>::~List()
{
if (this->ptr)
{
delete[] this->ptr;
}
cout<<"析构"<<endl;
}
template <typename T>
void List<T>::push_back(const T &v)
{
if (this->ptr)
{
T *temp_ptr=new T[this->length+1]();
memcpy(temp_ptr,this->ptr,sizeof(T)*this->length);
delete[] this->ptr;
this->ptr=temp_ptr;
}
else
{
this->ptr=new T[1]();
}
this->ptr[this->length++]=v;
}
template <typename T>
T List<T>::size()
{
return this->length;
}
template <typename T>
T & List<T>::operator[](int idx)
{
return this->ptr[idx];
}
int main()
{
List<int> L(3);
cout<<L.size()<<endl;
L.push_back(10);
L.push_back(20);
L.push_back(30);
cout<<L.size()<<endl;
cout<<L[3]<<endl;
return 0;
}
模板重载
#include <iostream>
using namespace std;
template <typename T> void mswap(T &a,T &b);
template <typename T> void mswap(T a[],T b[],int len);
template <typename T> void printArray(T arr[],int len);
int main()
{
int a=10,b=20;
cout<<a<<" "<<b<<endl;
mswap(a,b);
int arr1[3]={1,2,3};
int arr2[3]={4,5,6};
cout<<"******"<<endl;
printArray(arr1,3);
cout<<"******"<<endl;
printArray(arr2,3);
mswap(arr1,arr2,3);
cout<<"******"<<endl;
printArray(arr1,3);
cout<<"******"<<endl;
printArray(arr2,3);
return 0;
}
template <typename T> void mswap(T &a,T &b)
{
T temp=a;
a=b;
b=temp;
}
template <typename T> void mswap(T a[],T b[],int len)
{
T temp;
for (int i=0;i<len;i++)
{
temp=a[i];
a[i]=b[i];
b[i]=temp;
}
}
template <typename T> void printArray(T arr[],int len)
{
for (int i=0;i<len;i++)
{
cout<<arr[i]<<" ";
}
cout<<endl;
}
参数类型推断
类型转换
template <typename T> void func(T a, T b);
func(1,2.3);
template <typename T> void func(T a);
int a[10];
func(a);
template <typename T> void func(T &a);
int a[10];
func(a);
注意
当显示指明类型参数时,可以进行类型转换(隐式)
template <typename T> void func(T a, T b);
func<float>(1,2.3);
显示指明
template <typename T1,typename T2> func(T1 a)
{
T2 b;
}
func<int,int>(10)
模板进阶 – 还没看
7.6
|