演繹的過程:
描述實參-引數對匹配情況:
匹配型別a(來自實參的型別),引數化型別p(來自引數的宣告)
如果實參的是陣列或函式型別,那麼會發生decay轉型,轉化為對應的指標型別,同時還會忽略高層次的const和volatile限定符。
template void f(t); //p就是t
template void g(t&); //p仍然是t
double x[20];
int const seven = 7;
f(x); //t是double*
g(x); //t是double[20]
f(seven); //t是int
g(seven); //t是int const
f(7); //t是int
g(7); //錯誤,不能把傳遞給int&
演繹的上下文:
template
void f(t1 (t2::*) (t3*) );
class s ;
void g(int*** ppp)
演繹t1=void,t2=s,t3=double。
解釋:f的引數是乙個函式,函式的返回值是t1,函式的依賴關係由t2::*體現,函式的引數是t3*。
例:template
class x
};template
void fppm(void (x::*p)(typename x::i));
int main()
子構造x::i是乙個不可演繹的上下文,然而,具有成員指標型別的成員型別部分x是乙個可以演繹的上下文。
特殊的演繹情況:
1.取函式模板的位址
template
void f(t, t);
void (*pf) (char, char) = &f;
2.與轉型運算子模板一起出現
class s ;
void f(int (&)[20]);
void g(s s)
可接受的實參轉型:
1.如果原來宣告的引數是乙個引用引數子,那麼被替換的p型別可以比a型別多乙個const或volatile限定符
2.如果a型別是指標型別或者成員指標型別,那麼它可以進行限定符轉型,轉化為被替換的p型別
3.當演繹過程不涉及到轉型運算子模板的時候,被替換的p型別可以是a型別的基類,或者當a是指標型別時,p可以是乙個指標型別,它所指向的型別是a所指向的型別的基類。
類模板引數:
模板實參演繹只能應用於函式模板和成員函式模板,是不能應用於類模板的。對於類模板的建構函式,也不能根據實參來演繹類模板引數。
預設呼叫實參:
對於預設呼叫實參而言,即使不是依賴型的,也不能用於演繹模板實參:
template
void f(t x = 42)
int main()
C Templates 模板實戰
包含模型 把模板的定義包含在宣告模板的標頭檔案裡面,即讓定義和宣告都位於同乙個標頭檔案中。如果不需要考慮建立期的時間問題,建議盡量使用包含模型來組織模板 非內聯函式模板在呼叫的位置並不會被擴充套件,而是當它們基於某種型別進行例項化之後,才產生乙份新的 基於該型別的 函式拷貝。顯式例項化 顯式例項化指...
模板實參推斷
定義 從函式實參確定模板實參的型別和值的過程叫做模板實參推斷 c primer 4th 舉例 template 模板型別形參 int compare const glorp v1,const glorp v2 函式形參 模板實參推斷的規則 1 如果某個函式的多個形參的型別是同乙個模板型別形參,推斷出...
C Templates學習筆記五 模板實戰
使用分離模型 讓模板定義和宣告在不同的檔案裡可能會導致鏈結錯誤。為了解決這種問題,我們把模板的宣告和定義都放在同乙個標頭檔案裡。例如 ifdef myfirst hpp define myfirst hpp include include template void print typeof t c...