C 函式模板(泛型程式設計一)

2021-08-04 02:42:26 字數 3885 閱讀 2260

在c語言中為了**復用可以定義巨集**塊,但巨集**塊在預編譯的時候被整體替換掉了,編譯器並不知道巨集的存在,故缺少型別檢查。另巨集也不支援遞迴呼叫。在c++中為了**復用便運用泛型程式設計思想。c++用模板來實現泛型程式設計,模板分為函式模板類模板

1.函式模板定義

a.函式模板是一種特殊的函式,可用不同型別進行呼叫

b.看起來和普通函式很相似,區別是型別可被引數化。 

2.函式模板語法規則

template

void swap(t& a, t& b)

template關鍵字用於宣告開始進行泛型程式設計;

typename關鍵字用於宣告泛指型別。

3.函式模板的使用

a.自動推導呼叫

int a = 1;

int b = 3;

swap(a, b);

上述**中編譯器會自動推導泛指型別t為int

b.具體型別顯示呼叫

float c = 4;

float d = 5;

swap(c, d);

上述**顯示的指明泛指型別t為float

下面**給出函式模板的初步使用:

#include 

#include

using

namespace

std;

template

< typename t >

void swap(t& a, t& b)

template

< typename t >

void sort(t a, int len)}}

}template

< typename t >

void println(t a, int len)

cout

<< endl;

}int main()

; println(a, 5);

sort(a, 5);

println(a, 5);

string s[5] = ;

println(s, 5);

sort(s, 5);

println(s, 5);

return

0;}

執行結果如下所示:

4.編譯器如何編譯函式模板

a.編譯器從函式模板通過具體型別產生不同的函式;

b.編譯器會對函式模板進行兩次編譯,首先對模板**本身進行編譯,然後對引數替換後的**進行編譯。

c.函式模板本身不允許隱式型別轉換。當採用自動推導型別時,必須嚴格匹配;在顯示型別指定時,能夠進行隱式型別轉換。

下面分析如下**:

#include 

#include

using

namespace

std;

class test

};template

< typename t >

void swap(t& a, t& b)

typedef

void(funci)(int&, int&);

typedef

void(funcd)(double&, double&);

typedef

void(funct)(test&, test&);

int main()

執行結果如下所示:

從上圖顯示結果來看,指標pi和pd的值不相等,這便證明編譯器會對函式模板進行兩次編譯,且根據不同的泛指型別產生不同的函式。

5.多引數函式模板

函式模板可以定義任意多個不同的型別引數,如下所示:

template

t1 add(t2 a, t3 b)

對於多引數的函式模板和乙個引數的使用方法一樣,但如果返回值型別也是泛指型別時編譯器無法自動推導返回值型別,必須顯示指定。在顯示指定引數型別時,不一定要全部指定,可以從左到右部分指定型別引數,下面給出示例:

#include 

#include

using

namespace

std;

template

< typename t1, typename t2, typename t3 >

t1 add(t2 a, t3 b)

int main()

執行結果如下所示:

6.過載函式模板

函式模板可以像普通函式一樣被過載,有記下幾點需要注意:

a.c++編譯器優先考慮普通函式;

b.如果函式模板可以產生乙個更好的匹配,那麼選擇模板;

c.可以通過空模板實參列表限定編譯器只匹配模板。

分析如下**:

#include 

#include

using

namespace

std;

template

< typename t >

t max(t a, t b)

int max(int a, int b)

template

< typename t >

t max(t a, t b, t c)

int main()

執行結果如下所示:

7.函式模板特化

現分析下面**:

template t>

bool equal(t a, t b)

上面所示**為比較兩個物件之間是否相等,請看下面的呼叫:

cout << equal(1, 1) << endl;

cout << equal(0.1, 0.1) << endl;

會以int為泛指型別來呼叫函式模板,可以輸出正確的結果,但如果用下面的方式呼叫:

cout << equal(0.1, 0.1) << endl;
會以double為泛指型別來呼叫函式模板,但double型在記憶體中儲存方式並非精確儲存,所以比較兩個double型數不能用「==」來比較,故需要提供乙個函式特化,如下所示:

template

< >

bool equal(double a, double b)

函式模板(泛型程式設計)

函式模板就是將函式型別引數化,方便程式設計。1 普通函式模板 include using namespace std template template是告訴編譯器,要開始泛型程式設計了,並用t替代函式的引數型別 void myswap t a,t b template 定義兩個泛型,其實定義乙個也...

泛型程式設計 函式模板

當函式的業務邏輯相同但是函式的引數不相同時,讓型別引數化,讓程式設計師能夠方便程式設計,就用到了泛型程式設計。基本語法 includeusing namespace std 函式的業務邏輯一樣但是函式的引數不一樣 void myswap01 int a,int b void myswap02 cha...

C 泛型程式設計 函式模板 類模板

以前我們寫過乙個簡單的交換函式。我們不難發現交換函式是與型別有很大關係的,int,double.那麼如何實現乙個通用的交換函式呢?void swap int left,int right void swap double left,double right void swap char left,c...