下面是我不理解如何是模板,和專門的模板
#include<iostream>
using namespace std;
template <typename T>
T calc(T, T) { cout << "template calc" << endl; }
double calc(double, double) { cout << "ordinary calc" << endl; }
template <>
char calc<char>(char, char) { cout << "template specialisation calc" << endl; }
int main() {
int ival;
double dval;
float fd;
calc(0, ival); // calls the generic calc(T, T)
// the following all call calc(double, double)
calc(0.25, dval);
calc(0, fd);
calc(0, 'J');
calc('I', 'J'); // calls calc(char, char)
}
的代碼有5個函數調用calc下,所以我稱它們爲:1) - 5)根據他們的位置。
1)有道理。 0是一個整數,ival是一個整數,所以calc(T,T)被調用是有意義的。雖然我覺得我的理由是錯誤的。畢竟,它們都是雙打的,所以如果調用calc(double,double),那也是有意義的。所以在這裏尋找澄清。
2)沒有戲劇,都是雙打,打電話calc(雙,雙)。簡單。
3)fd是一個浮點數。可以調用calc(T,T)或calc(double,double)。因爲1)導致了對calc(T,T)的調用,我會假設同樣會在這裏持續下去,因爲我們再次有一個參數爲0,但是這叫做calc(double,double)。所以這使我感到困惑,特別是這與1)
4)我的第一個想法是0是一個有效的字符,所以是'J',所以它調用calc(char,char)。它可能使用普通類型的整數調用calc(T,T)。但不是,都是錯誤的,它叫calc(雙倍,雙倍)。我對這個很困惑。對我沒有意義。
5)是有道理的,但只有當我應用與4)相同的邏輯時,這在4)是錯誤的,所以如果我看到另一個使用模板的例子,我不確定什麼是什麼適用的邏輯。
所以尋找解釋爲什麼這個程序做它做的。
謝謝。
在靜態綁定中,編譯器更喜歡普通的重載規則來模板專門化:只有當它無法找出對於參數在手的很好的重載時,它纔會使用後者。不過,我不能引用標準的相關部分。 – akappa
如果函數模板參數不完全匹配*(即需要隱式類型轉換),則不會將該模板視爲候選項。 –
@n.m .:但即使在這種情況下,編譯器也會更喜歡重載,即使它需要一些轉換才能調用它,對嗎? – akappa