一.概述

二.函数模板

1.概述

(1)介绍

C++的函数模板在一定程度上类似于Java的泛型,可以类比学习

编译次数:函数模板会编译两次,一次是对函数模板本身的编译,一次是在调用函数模板时,会将T的类型具体化,然后再编译一次

**函数模板的目标:**函数模板是为了实现泛型,可以减轻编程的工作量,增强函数的重用性

**参数类型的来源:**在调用函数模板时

  • 如果没有显示的指定函数模板的类型,编译器会根据传入的参数自动推导类型,并对模板中类型的代号进行替换
  • 如果显示制定了函数模板的类型,那编译器就会直接以指定的类型替换函数模板中的类型

(2)注意事项

  • 函数模板和普通函数都识别时,编译器默认会优先选择普通函数

    因为可以减少编译的次数

  • 函数模板和普通函数都识别时,可以通过显示指定使用函数模板,使编译器选择函数模板

    在函数名后附加<>,可以指定使用函数模板。例如:Test<>(1,2)

  • 函数模板自动类型推导时,不能对函数的参数进行自动类型转换

    • 显示指定模板类型时,是可以进行自动类型转换的,即小类型to大类型

      Test(10,'b');//里面的b字符会被替换成ASCII码-98
      

2.格式

(1)参数

下面的T是类型占位符,可以任意取的,且该数据类型只在函数模板内有效

  • template :函数模板的定义
    • typename T 用于告知编译器T是一个数据类型
  • T parameter1, T parameter2:函数的参数列表
    • 用函数模板定义的T作为参数的数据类型

(2)格式:

template 返回值类型 函数名才是真正的函数模板,也只有他才能代表函数模板

template //可以声明一个类型,也可以声明多个类型
返回值类型 函数名(T parameter1, V parameter2) {
    // 函数实现
}

(3)示例

下面交换元素信息的函数模板,不论传入什么类型都可以调用

#include 
using namespace std;

/*函数模板*/
//template声明的类型只在函数模板内有效
template void exchange(T data1,T data2){
    T temp = data1;
    data1 = data2;
    data2 = temp;

    cout << "data1:" << data1 << " data2: " << data2 << endl;
}

int main(){
    /*调用函数模板*/

    //编译器自动类型推导
    exchange(10,20);
    exchange('a','b');
    //显示指定模板的数据类型
    exchange(30,40);
}
/*
data1:20 data2: 10
data1:b data2: a
data1:40 data2: 30
*/

3.函数模板重载

① 概述

重载的规则和普通函数重载一致,让函数参数、个数、顺序不同即可

② 示例
template
void exchange(T data){
    cout << data << endl;
}
/*重载函数模板*/
template
void exchange(T data1,T data2){
    T temp = data1;
    data1 = data2;
    data2 = temp;
    cout << "data1:" << data1 << " data2: " << data2 << endl;
}

4.局限性

(1)概述

当函数模板推出的类型是数组或则是其它自定义类型时,可能会运算符不识别,此时,可以采取运算符重载具体化函数模板的形式进行解决

(2)运算符重载

① 概述

根据编辑器的提示,重写不识别的运算符即可

对不识别的运算符进行重载,使其能够正常运行即可

image-20240317150301358
② 示例
#include 
using namespace std;

class Data{
public:
    int data;
public:
    Data(){
        this->data = 0;
    }
    Data(int x){
        this ->data =x;
    }
};

/*函数模板*/
//template声明的类型只在函数模板内有效
template
void exchange(T data1,T data2){
    T temp = data1;
    data1 = data2;
    data2 = temp;
    cout << "data1:" << data1 << " data2: " << data2 << endl;
}
/*重写报异常的<<运算符*/
ostream & operator<<(ostream & out,Data obj){
    out << obj.data;
    return out;
}


int main(){
    Data data1(1);
    Data data2(2);
    exchange(data1,data2);
}

(3)具体化函数模板

① 概述

概述: 就是具体指明函数模板中的泛型是什么数据类型

② 格式

格式: 具体化函数模板的时候,template后的<> 不用指定内容

template<> 数据类型 函数名<具体化的类型>(数据类型 对象名){
    
}

例子:

template<>
void exchange(Data data1,Data data2){
    Data temp = data1;
    data1 = data2;
    data2 = temp;
    cout << "data1:" << data1.data << " data2: " << data2.data << endl;
}
③ 示例
#include 
using namespace std;

class Data{
public:
    int data;
public:
    Data(){
        this->data = 0;
    }
    Data(int x){
        this ->data =x;
    }
};

/*函数模板*/
//template声明的类型只在函数模板内有效
template
void exchange(T data1,T data2){
    T temp = data1;
    data1 = data2;
    data2 = temp;
    cout << "data1:" << data1 << " data2: " << data2 << endl;
}

/*具体化函数模板*/
template<>
void exchange(Data data1,Data data2){
    Data temp = data1;
    data1 = data2;
    data2 = temp;
    cout << "data1:" << data1.data << " data2: " << data2.data << endl;
}

int main(){
    Data data1(1);
    Data data2(2);
    exchange(data1,data2);
}

三.类模板

1.概述

简述: 类模板是一种特殊类型的类,它允许程序员编写一个通用的类定义,这个类可以与多种不同的数据类型一起工作。通过使用模板,我们可以编写一个代码,它可以在多种数据类型上工作,而无需为每种数据类型重写代码

注意事项:

  • 使用类模板必须显式的指定类模板的数据类型

2.格式

使用template关键字声明的类型用于定义类内的成员

(1)简述

类模板的声明使用template关键字,后面跟着尖括号中的模板参数列表。模板参数列表可以包含一个或多个类型参数。

(2)格式

类模板的是template class MyClass这一个整体,无论是声明友元还是类外实现类模板内函数,都要以其作为函数名

定义:

template   
class MyClass {  
public:  
    T value;  
      
    MyClass(T val) : value(val) {}  
      
    void printValue() {  
        std::cout << "Value: " << value << std::endl;  
    }  
};

使用类模板创建对象:

创建类模板对象时,要在<> 显式制定类型

MyClass ob(value);

(3)示例

定义了一个名为Data的类模板,并使用类模板创建了对象0b1,并调用了类模板的showData方法

#include 
using namespace std;

template
class Data{
public:
    T1 a;
    T2 b;
public:
    Data(){}
    Data(T1 a,T2 b){
        this -> a = a;
        this -> b = b;
    }
    void showData(){
        cout << a << " " << b < ob1(10,20);
    ob1.showDat
最后修改:2024 年 03 月 18 日
如果觉得我的文章对你有用,请随意赞赏