c++函数模板类模板


#define _CRT_SECURE_NO_WARNINGS

#include <iostream>

using namespace std;


//模板技术,类型参数化,编写代码时可以忽略类型
//为了让编译器区分是普通函数还是函数模板,引入关键字template
//也可以写成template<typename T>,两个意义是完全一样的,用标志T代表任意类型,即把类型参数化
//template<class T>只对后面紧跟着的第一个函数有作用,对第二个就没效果了,如果想再声明第二个函数模板,就需要再写一次template<class T>
template<class T>
//函数模板不会进行类型转换,即当函数模板的参数类型都一致时,你传入的参数类型也必须一致,它不像普通函数,你传入的类型不对应时,会自动转换成对应类型
void MySwap1(T &a, T &b)
{
T temp = a;//函数模板里所有类型都为自定义的T类型,使类型参数化
a = b;
b = temp;
}

void MySwap1(int &a, int &b)
{
//函数模板和普通函数之间是叫重载吗???,但系统会优先考虑普通函数,即当业务有两种选择的时候,一定是选普通函数,当普通函数不满足的时候,再去调用函数模板
}

template<class T>//只修饰一个函数,且类型标志符一样也互不影响
void MySwap2(T &a, T &b)
{
T temp = a;//函数模板里所有类型都为自定义的T类型,使类型参数化
a = b;
b = temp;
}

template<class T>
void MySwap2(T &a)//函数模板和函数模板之间也可以重载,函数参数类型不同就可以了
{
T temp = a;//函数模板里所有类型都为自定义的T类型,使类型参数化
}

//函数模板可以定义多个类型
template<class T1, class T2, class T3>
T1 MySwap3(T1 a, T2 b, T3 c)//不能进行自动类型转换只是在形参的配上中,在函数体内是可以为不同类型赋值,仍满足规则
{
a = b;
b = c;
c = a;
return a;
}

//类模板,是成员变量类型参数化
template<class T>
class Person
{
public:
Person(T id, T age)
{
this->id = id;
this->age = age;
}
void show()
{
cout << "id=" << id << endl;
cout << "age=" << age << endl;
}
private:
T id;
T age;
};

template<class T>
void printArray(T *array, int len)
{
int i = 0;
for (i = 0; i < len; i++)
{
cout << array[i] << " ";
}
cout << endl;
}
template<class T>
void mySort(T *array, int len)
{
int i, j;
for (i = 0; i < len - 1; i++)
{
for (j = i + 1; j < len; j++)
{
if (array[i] < array[j])
{
T temp;
temp = array[i];
array[i] = array[j];
array[j] = temp;
}
}
}
}

//编译.c文件时用gcc,编译.cpp文件时用g++(linux环境下)
//c/c++编译流程:
//1.预编译,.cpp/.c文件生成.i文件
//2.编译,.i文件生成.s文件(即汇编文件)
//3.汇编,.s文件生成.o/.obj文件(linux下为.o文件,windows下为.obj文件)(即目标文件,二进制文件)
//4.链接,.o/.obj生成.o/.exe文件(linux下为.o文件,windows下为.exe文件)(即可执行文件)

int main()
{
int a = 10;
int b = 20;
//1.自动类型推导
MySwap1(a, b);//在模板函数中,因为是忽略类型的,因此编译器是不知道a和b的类型的,尽管你明确定义了a和b为int类型,编译器会根据数值自己推断传入的a和b是什么类型的值
//2.显式的指定类型
MySwap1<int>(a, b);//这就是显式的告诉编译器,我传进来的a和b的类型为int类型

//函数模板的实现原理:
//函数模板根据传进来的类型创建确定类型的模板函数,然后通过调用确定的模板函数进行业务
MySwap3(1, 'a', 2);


//函数模板可以自动推导类型
//类模板必须显式指定T类型,即在构造时指定类模板对象的类型
Person<int> p(1, 2);
p.show();

int intArray[] = { 2,4,7,9,1,6 };
int intLen = sizeof(intArray) / sizeof(int);
cout << "intLen=" << intLen << endl;
printArray(intArray, intLen);
mySort(intArray, intLen);
printArray(intArray, intLen);
char charArray[] = { 'c', 'a', 'b', 'w', 'z' };
int charLen = sizeof(charArray) / sizeof(char);
printArray(charArray, charLen);
mySort(charArray, charLen);
printArray(charArray, charLen);

return 0;
}

猜你喜欢

转载自blog.csdn.net/tulipless/article/details/80939821