STL分析-準備工作<一>

泛型設計之要點


模板發展起來,在c++語言發展過程中屬於意外發現,因而和基本的語法比較起來,是二等公民,語法支持不那麼優雅,代碼形式看着讓人很受傷,
C++11出來後,估計能好點,VS2010就引人了一些新特性,簡化了部分模板語法。
雖然模板在c++語法層面屬於二等公民,但是,從現在的趨勢來看,這幾年c++的主要改進點基本都集中在模板和模板相關的這塊,這塊也是C++和其他其他語言相抗衡的主要力量。

要分析STL,模板是基本的技術基礎,關於模板的基礎語法,這兒不談了,主要談下一些要點和難點


泛型設計之要點——模板推導順序


模板分函數模板和類模板,類模板支持偏特化(有點像高等數學中的偏導數),這是泛型編程的絕大多技術,技巧的根源。函數模板不支持偏特化,類似類模板偏特化的那些東西其實是函數重載。

(1)函數 模板的匹配規則
非模板函數具有最高的優先權。如果不存在匹配的非模板函數的話,那麼最匹配的和最特化的函數具有高優先權

  1. 普通非模板函數在參數匹配時如果和模板函數匹配度一樣好,優先選擇普通函數,因爲一等公民嘛
  2. 幾個主模板函數中選擇匹配最好的
  3. 如果2選擇不出,選擇“最特化”的,最特化的如果又對模板實參做了特話,這個會被選中
  4. 出現二義性

模板特化不參與重載推導

template<class T>
void f(T);
template<>
void f<int*>(int*)
template<class T>
void f(T*)

答案是 第三個

(2) 類模板的匹配規則

最優化的優於次特化的,即模板參數最精確匹配的具有最高的優先權

例子:

template <class T> class vector{//…//}; // (a)   普通型
template <class T> class vector<T*>{//…//};   // (b) 對指針類型特化
template <>    class vector <void*>{//…//};   // (c) 對void*進行特化

每個類型都可以用作普通型(a)的參數,但只有指針類型才能用作(b)的參數,而只有void*才能作爲(c)的參數


泛型設計之要點——模板特化


模板有兩種特化,全特化和偏特化(局部特化)

模板函數只能全特化,沒有偏特化(以後可能有)。
模板類是可以全特化和偏特化的。
全特化,就是模板中模板參數全被指定爲確定的類型。
全特化也就是定義了一個全新的類型,全特化的類中的函數可以與模板類不一樣。

偏特化,就是模板中的模板參數沒有被全部確定,需要編譯器在編譯時進行確定。
在泛型中,利用特化類得到類新的特性,以便找到最適合這種特性的實現。而這一切都是在編譯時完成。

模板的特化是非常有用的。它像一個在編譯期的條件判斷。當編譯器在編譯時找到了符合的特化實現,就會使用這個特化實現。這就叫編譯器多態(或者叫靜態多態)。這種東西對編寫基礎庫是很有用的。這也就是爲何c++的基礎庫大量使用了模板技術,而且大量使用了特化,特別是偏特化。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章