1.问题
求两个较大值函数max(a,b),对于a,b的不同类型,都有相同的处理形式:return a< b?b:a;
方法:
(1)宏替换#define max(a,b) ((a) < (b)) ? (b) : (a) 。问题:不做类型检查
(2)重载:为每个类型提供一个重载版本,程序自己维护这些重载的版本
(3)函数模板:为相同逻辑功能提供一个模板,将类型当做参数传递,让编译器实例化对应版本的函数处理。不同版本由编译器维护
2.模板
(1)模板是一种参数化的多态工具(静态多态)
(2)所谓参数化的多态,是指将程序所处理的对象的类型参数化,使一段程序代码可以用于处理不同类型的对象
(3)采用模板编程,可以为各种逻辑功能相同而数据类型不同的程序提供一种代码共享机制
3.模板分类
模板分类:函数模板(function template),类模板(class template)
函数模板
[1]模板形参在模板中作为一种类型使用,可以用于函数的形参,函数返回值和函数的局部变量
[2]每个模板形参要在函数的形参列表中至少出现一次
[3]模板参数名的作用域限于函数模板的范围内
函数模板使用
[1]函数模板为所有函数提供唯一的一段函数代码,增强了函数设计的通用性
[2]使用函数模板的方法是先说明函数模板,然后实例化成相应的模板函数进行调用执行
1)函数模板不是函数,不能执行
2)置换代码中的类型参数得到模板函数---实例化
3)实例化后的模板函数是真正的函数,可以被执行
[3]模板被编译两次
1)实例化之前,先检查模板代码本身,查看语法是否正确:在这里会发现语法错误,如果遗漏分号等。
2)实例化期间,检查模板代码,查看是否所有的调用都有效。在这里会发现无效的调用,如该实例化类型不支持某些函数调用等。
[4]普通函数只需声明,即可顺利编译,而模板的编译需要查看模板的定义
函数模板特化
重载函数模板
#include <iostream>
#include <stdio.h>
#include <string.h>
using namespace std;
class Test {
public:
friend bool operator<(const Test& t1,const Test& t2) {
return true;
}
};
template<typename T>
const T& max(const T& t1, const T& t2) {
cout << "template function" << endl;
return t1 < t2? t2:t1;
}
//非模板函数重载
const int& max(const int& a,const int& b) {
cout << "non template function" << endl;
return a < b ? b: a;
}
//函数模板重载
template<typename T>
const T& max(const T& t1, const T& t2, const T& t3) {
cout << "template function" << endl;
return t1 < ::max(t2, t3)? ::max(t2, t3): t1;
}
//函数模板特化
template<>
const char* const& max(const char* const& t1, const char* const& t2) {
//const char*& max(const char*& t1, const char*& t2) {
return strcmp(t1, t2) < 0? t2: t1;
}
template<>
const char* const& max(const char* const& t1, const char* const& t2, const char* const& t3) {
return strcmp(t1, ::max(t2, t3)) <0? ::max(t2, t3): t1;
}
int main() {
Test t1,t2;
::max(t1, t2);
::max(Test(), Test());
//cout << ::max(Test(), Test()) << endl;
//cout << ::max("aaa", "zzz") << endl;
const char* t3 = "aaa";
const char* t4 = "zzz";
const char* t5 = "bbb";
cout << ::max(t3, t4) << endl;
cout << ::max(t3, t4, t5) << endl;
cout << ::max(200, 100, 5) << endl;
cout << ::max('a', 100) << endl; //const int& max(const int& a,const int& b)
cout << ::max<int>('a', 100) << endl; //显示指定模板函数
cout << ::max(97, 100) << endl; //const int& max(const int& a,const int& b)
cout << ::max<>(97, 100) << endl; //自动推导
cout << ::max<int>(99, 2000) << endl; //显示指定模板函数
cout << ::max('a', 'c') << endl; //自动推导
return 0;
}