新聞中心
為什么需要模板
相信寫(xiě)過(guò)Java的童鞋們都知道泛型編程,在C++中與之對(duì)應(yīng)的就是模板。

創(chuàng)新互聯(lián)主營(yíng)海城網(wǎng)站建設(shè)的網(wǎng)絡(luò)公司,主營(yíng)網(wǎng)站建設(shè)方案,重慶App定制開(kāi)發(fā),海城h5重慶小程序開(kāi)發(fā)搭建,海城網(wǎng)站營(yíng)銷(xiāo)推廣歡迎海城等地區(qū)企業(yè)咨詢(xún)
模板是一種對(duì)類(lèi)型進(jìn)行參數(shù)化的工具,通常有兩種形式:函數(shù)模板和類(lèi)模板。
模板是一些為多種類(lèi)型而編寫(xiě)的函數(shù)和類(lèi),而且這些類(lèi)型都沒(méi)有指定。當(dāng)使用模板的時(shí)候,你只需要把所希望的類(lèi)型作為一個(gè)(顯式或者隱式的)實(shí)參傳遞給模板。 另外,由于模板是語(yǔ)言本身所具有的特性,所以它完全支持類(lèi)型檢查和作用域。使用模板的目的就是能夠讓程序員編寫(xiě)與類(lèi)型無(wú)關(guān)的代碼,盡可能地減少重復(fù)代碼。
眾所周知,C++是一門(mén)強(qiáng)類(lèi)型的靜態(tài)語(yǔ)言。在聲明變量、函數(shù)和大多數(shù)其他類(lèi)型的實(shí)體的時(shí)候,C++要求我們使用指定的類(lèi)型。 然而,對(duì)于許多代碼,除了類(lèi)型不同之外,其余的代碼看起來(lái)都是相同的。例如我們需要實(shí)現(xiàn)一個(gè)交換兩個(gè)變量的函數(shù),為了通用性, 這個(gè)交換變量的函數(shù)不能固定兩個(gè)變量的類(lèi)型,這就使得模版橫空出世。。。
在C++標(biāo)準(zhǔn)庫(kù)中,幾乎所有的代碼都是模板代碼,可以說(shuō)沒(méi)有C++模板就沒(méi)有STL。
模板函數(shù)
首先我們看下函數(shù)模板的格式:
template
返回類(lèi)型 函數(shù)名(參數(shù)列表)
{
函數(shù)體
} 或者使用class關(guān)鍵字也可:
template
返回類(lèi)型 函數(shù)名(參數(shù)列表)
{
函數(shù)體
} 為什么會(huì)有兩種不同的格式呢?這是因?yàn)殍b于歷史的原因,你可能還會(huì)使用class取代typename,來(lái)定義類(lèi)型參數(shù)。 在C++語(yǔ)言的演化過(guò)程中,關(guān)鍵字typename的出現(xiàn)相對(duì)較晚一些;在它之前,關(guān)鍵字class是引入類(lèi)型參數(shù)的唯一方式,并一直作為有效方式保留下來(lái)。 但是更加標(biāo)準(zhǔn)的格式是使用typename關(guān)鍵字。
例如我們使用模板定義了返回較大值的模板函數(shù):
template
const T& max_fun(const T& a,const T& b){
return a >= b? a:b;
} 下面我們調(diào)用一下我們定義的模板函數(shù)max_fun:
int main(int argc, char* argv[]) {
// 都是int類(lèi)型 ok
int max = max_fun(10,10);
// 都是double類(lèi)型 ok
int max = max_fun(10,10);
// 一個(gè)int類(lèi)型,一個(gè)double類(lèi)型 編譯不通過(guò)
int max = max_fun(10,11.0);
std::cout << "max:" << max << std::endl;
return 0;
}在上面的例子中我們發(fā)現(xiàn)函數(shù)max_fun(10,11.0)報(bào)錯(cuò)了,無(wú)法編譯通過(guò),這是為什么呢?因?yàn)槲覀兌x的模板函數(shù)max_fun只有一個(gè)參數(shù)類(lèi)型, 但是max_fun(10,11.0)卻傳了兩個(gè)不同的參數(shù)類(lèi)型,二載函數(shù)模板中是不允許進(jìn)行自動(dòng)類(lèi)型轉(zhuǎn)換的,因此報(bào)錯(cuò),有兩種方式可以解決這個(gè)報(bào)錯(cuò):
- 一是對(duì)實(shí)參進(jìn)行強(qiáng)制類(lèi)型轉(zhuǎn)換,使它們可以互相匹配:
max_fun(10,static_cast(11.0)); - 二是顯式指定(或者限定)T的類(lèi)型:
max_fun(10,11.0); 重點(diǎn):在函數(shù)模板實(shí)參演繹的過(guò)程中,是不允許進(jìn)行自動(dòng)類(lèi)型轉(zhuǎn)換的。
重載函數(shù)模板
模板函數(shù)在使用時(shí)編譯器回自動(dòng)實(shí)現(xiàn)實(shí)例化,只要使用函數(shù)模板,(編譯器)會(huì)自動(dòng)地引發(fā)這樣一個(gè)實(shí)例化過(guò)程,因此程序員并不需要額外地請(qǐng)求模板的實(shí)例化。
和普通函數(shù)一樣,函數(shù)模板也可以被重載。就是說(shuō),相同的函數(shù)名稱(chēng)可以根據(jù)不同的函數(shù)參數(shù)具有不同的函數(shù)定義; 于是,當(dāng)使用函數(shù)名稱(chēng)進(jìn)行函數(shù)調(diào)用的時(shí)候,C++編譯器必須決定究竟要調(diào)用哪個(gè)候選函數(shù)。
一個(gè)非模板函數(shù)可以和一個(gè)同名的函數(shù)模板同時(shí)存在,而且該函數(shù)模板還可以被實(shí)例化為這個(gè)非模板函數(shù)。 對(duì)于非模板函數(shù)和同名的函數(shù)模板,如果其他條件都是相同的話(huà),那么在調(diào)用的時(shí)候,重載解析過(guò)程通常會(huì)調(diào)用非模板函數(shù),而不會(huì)從該模板產(chǎn)生出一個(gè)實(shí)例。
下面我們通過(guò)一個(gè)小例子來(lái)了解下重載函數(shù)模板:
#include
#include
template
const T& max_fun(const T& a,const T& b){
std::cout << "模板類(lèi)型max_fun:"<< std::endl;
return a >= b? a:b;
}
const int& max_fun(const int& a,const int& b){
std::cout << "int 類(lèi)型max_fun:"<< std::endl;
return a >= b? a:b;
}
int main(int argc, char* argv[]) {
// 都是double類(lèi)型 匹配到模板函數(shù)max_fun
// int max = max_fun(10.0,11.0);
// 都是int類(lèi)型 匹配到 普通函數(shù)max_fun
// int max = max_fun(10,10);
// 一個(gè)char類(lèi)型,一個(gè)double類(lèi)型 匹配到普通函數(shù)max_fun
int max = max_fun('a',11.0);
std::cout << "max:" << max << std::endl;
return 0;
} 在上面的例子main函數(shù)中我們多次調(diào)用了函數(shù)max_fun,那么怎么區(qū)分是調(diào)用了模板函數(shù)max_fun還是調(diào)用了重載的普通函數(shù)max_fun呢?
有一條規(guī)則是這樣的:
一個(gè)非模板函數(shù)可以和一個(gè)同名的函數(shù)模板同時(shí)存在,而且該函數(shù)模板還可以被實(shí)例化為這個(gè)非模板函數(shù)。對(duì)于非模板函數(shù)和同名的函數(shù)模板,如果其他條件都是相同的話(huà),那么在調(diào)用的時(shí)候,重載解析過(guò)程通常會(huì)調(diào)用非模板函數(shù),而不會(huì)從該模板產(chǎn)生出一個(gè)實(shí)例。
因此在上面的例子中我們可以很容易地看出第17行調(diào)用的是模板函數(shù)max_fun,因?yàn)闆](méi)有參數(shù)是double類(lèi)型的max_fun被重載。 但在第19行因?yàn)橛幸粋€(gè)參數(shù)是int類(lèi)型的重載函數(shù)max_fun,因此這一行調(diào)用的是普通重載函數(shù)max_fun。
那么在第21行也是調(diào)用了int類(lèi)型的重載函數(shù)max_fun,這是為什么呢?
這是因?yàn)槟0迨遣辉试S自動(dòng)類(lèi)型轉(zhuǎn)化的,但普通函數(shù)可以進(jìn)行自動(dòng)類(lèi)型轉(zhuǎn)換,所以第21行調(diào)用的是int類(lèi)型的重載函數(shù)max_fun(‘a(chǎn)’和11.0都被轉(zhuǎn)化為int)。
函數(shù)重載應(yīng)該牢記一條首要規(guī)則:函數(shù)的所有重載版本的聲明都應(yīng)該位于該函數(shù)被調(diào)用的位置之前。
文章名稱(chēng):C++之函數(shù)模板
文章網(wǎng)址:http://www.dlmjj.cn/article/dpspscp.html


咨詢(xún)
建站咨詢(xún)
