模板的使用

本文介绍了C++中的泛型编程,重点讲解了函数模板和类模板的概念、使用方法及调用规则。通过实例展示了如何使用函数模板实现通用的交换功能,并对比了普通函数与函数模板的区别,包括类型匹配、类型转换和调用时机。同时,讨论了模板的局限性和函数模板的重载情况,强调了在不同参数列表和个数下的重载实现。
摘要由CSDN通过智能技术生成

模板:

泛型编程:用一个标志来表示类型,不是实际的类型。独立于任何特定类型的编程,c++的一个部分。

C++提供两种模板:函数模板和类模板。

函数模板:

   作用:建立通用函数,其函数返回值类型和形参类型可以不具体制定,用一个虚拟的类型代表。
   格式:template<class T1,typename T2>
             返回值 函数名(参数){  }
   解释: template  ----- 声明创建模板
               typename ----- (也可以用class代替)表明后的类型是一个通用类型,或许叫做虚拟类型
               T1-------------- 通用类型或者虚拟类型,可以在函数中直接当做普通类型使用。

函数模板的调用:
     第一种:函数名 <实际类型1,实际类型2>(参数列表);
                   显式类型推导   fun<int>(1,2);
     第二种:函数名(参数);
                   隐形类型推导

 注意:显示类型推导 参数和推导的类型必须一致。
            如果有普通函数和模板函数,在调用时可以用显示调用,省略类型的方式  swap<>(1,2)。

 实例:

#include <iostream>
using namespace std;
 
//两个整型交换函数
void swapint(int& a, int& b)
{
	int temp = a;
	a = b;
	b = temp;
}
 
//两个浮点型数据交换函数
void swapdouble(double& a, double& b)
{
	double temp = a;
	a = b;
	b = temp;
}
 
void test1()
{
	int a = 10;
	int b = 20;
	swapint(a, b);
	cout << "a=" << a << endl;
	cout << "b=" << b << endl;
 
	double c = 1.1;
	double d = 2.2;
	swapdouble(c, d);
	cout << "c=" << c << endl;
	cout << "d=" << d << endl;
}
 
//函数模板
template<typename T>//声明一个模板,提供一个通用的数据类型T
void myswap(T& a, T& b)
{
	T temp = a;
	a = b;
	b = temp;
}
 
void test2()
{
	int a = 10;
	int b = 20;
	//利用函数模板交换
	//两种方式使用函数模板
	//1.自动类型推导
	//myswap(a, b);//隐式推导
	//myswap<int>(a, b);//显式推导
	cout << "a=" << a << endl;
	cout << "b=" << b << endl;
 
	double c = 1.1;
	double d = 2.2;
	
	cout << "c=" << c << endl;
	cout << "d=" << d << endl;
}
int main(){
	void test1();
	void test2();
	system("pause");
	return 0;
	
}

普通函数和函数模板的区别:
   (1) 函数只可以有一种数据类型相匹配。模板有多种类型
   (2) 隐式推导优先使用普通函数,只有普通函数不匹配才使用函数模板
   (3)函数模板只有在调用时,才会构建函数,而普通函数是在编译时。
   (4)普通函数调用时候可以发生自动类型转换,而函数模板不行。 

//普通函数
int myadd(int a, int b)
{
	return a + b;
}
 
void test1()
{
	int a = 10;
	int b = 20;
	int c = 'c';
	cout <<myadd(a,b) << endl;
	cout << myadd(a, c) << endl;//自动将字符转化成整数
}
 
//函数模板
template<class T>
T myadd2(T a, T b)
{
	return a + b;
}
 
void test2()
{
	int a = 10;
	int b = 20;
	char c = 'c';
	//自动类型推导,不发生隐式类型转换
	cout << myadd2(a, b) << endl;
	//cout << myadd2(a, c) << endl;//无法自动转换
 
	//显示指定类型
	cout << myadd2<int>(a, c) << endl;
}

普通函数与函数模板的调用规则:

(1).如果函数模板和普通函数都可以实现,优先调用普通函数。

(2).可以通过空模板参数列表来强制调用函数模板。

(3).函数模板也可以发生重载。

(4).如果函数模板可以产生更好的匹配,优先调用函数模板。

  模板的局限性:

      某些特殊数据类型不能直接使用模板进行运算,需要进行实例化对其特殊运算。

  函数模板重载:
      和普通函数的重载相似。也是同一个作用域类函数名相同参数列表不同。
     参数顺序不同的重载:
         template <class T1,class T2>void swap1(T2 a,T1 b)
          template <class T1,class T2>void swap1(T1 a,T2 b)
   
     参数个数不同的重载:
         template <class T1,class T2>   void swap1(T1 a,T2 b)
         template <typename T2>  void swap1(T2 t)
         传入不同的参数,调用不同的版本

     注意

        在函数参数顺序不同的重载中,实例化的时候不可以是相同类型
         例如  swap1<int ,int >(1,2)则没法匹配哪个函数。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值