函数模板
- 泛型编程 – 模板技术 特点:类型参数化
- template< typename T > 告诉编译器后面紧跟着的函数或者类中出现T,不要报错,T是一个通用的数据类型
- 实现通用两个数进行交换函数
- 使用
- 自动类型推导 必须要推导出一致的T才可以使用
- 示指定类型 mySwap<int>(a,b);
函数模板和普通函数的区别以及调用规则
- 区别
- 如果使用自动类型推导,是不可以发生隐式类型转换的
- 普通函数 可以发生隐式类型转换
- 调用规则
- 如果函数模板和普通函数都可以调用,那么优先调用普通函数
- 如果想强制调用函数模板,可以使用空模板参数列表
- myPrint<>(a, b);
- 函数模板也可以发生函数重载
- 如果函数模板能产生更好的匹配,那么优先使用函数模板
模板的实现机制
- 编译器并不是把函数模板处理成能够处理任何类型的函数
- 函数模板通过具体类型产生不同的函数 --- 通过函数模板产生的函数 称为模板函数
- 编译器会对函数模板进行两次编译,在声明的地方对模板代码本身进行编译,在调用的地方对参数替换后的代码进行编译。
模板局限性
- 模板并不是真实的通用,对于自定义数据类型,可以使用具体化技术,实现对自定义数据类型特殊使用
#include<iostream>
#include<string>
using namespace std;
class person {
public:
string name;
int age;
person(string name, int age) :name(name),age(age){}
};
template<typename T>
void mySwap(T &a,T &b) {
T temp = a;
a = b;
b = temp;
}
template<class T>
void arr_sort(T arr[],int len) {
for (int i = 0;i<len;i++) {
for (int j = i+1;j<len;j++) {
if (arr[i]<arr[j]) {
T temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
}
}
}
}
template<class T>
void print_arr(T arr[],int len) {
for (int i = 0; i < len;i++) {
cout << arr[i] << " ";
}
}
template<class T>
bool compare_obj(T &a,T &b) {
if (a==b) {
return true;
}
return false;
}
//对复杂数据类型具体化
template<> bool compare_obj(person &a,person &b) {
if (a.age==b.age&&a.name==b.name) {
return true;
}
return false;
}
void test() {
int a = 10;
int b = 20;
mySwap(a, b);
cout << a << endl;
cout << b << endl;
double c = 3.14;
double d = 1.2;
mySwap<double>(c, d);
cout << c << endl;
cout << d << endl;
char str[10] = "abcdefg";
arr_sort(str,strlen(str));
print_arr(str,strlen(str));
int arr[10] = { 1,5,3,7,2,8,9,19,12,30 };
arr_sort(arr, 10);
print_arr<>(arr, 10);
person p1("Tom", 21);
person p2("Tom", 21);
cout << "\nresult: " << compare_obj(p1, p2) << endl;
}
int main() {
test();
system("pause");
return EXIT_SUCCESS;
}