您面臨的問題與T
有關,可能是int
或float
。
如果你看一下模板類的定義,你會此話是那typename
後出現在template
部分相同T
也表現爲參數的Set
方法。
這意味着,當你說話的Point<int>
那麼只有一個Set
定義的方法,它有兩個int
。而且每個不同的Point<T>
都會有自己的Set(T,T)
方法。
如果你希望有一個不同的Set
方法,那麼你需要的模板類中聲明模板Set
,這樣做是像這樣:
template <typename T>
class Point
{
public:
template <typename Num>
void Set(Num x, Num y);
};
注意我如何不得不選擇了不同的模板參數名稱。
爲了解決你的問題,你可以介紹另一種方法,float
,但你得有另一爲double
,並long double
...它很快會變得困難。
最簡單的辦法,就是去暴力破解:
template <typename Integral>
template <typename Num>
void Point<Integral>::Set(Num x, Num y)
{
this->x = long double(x) + 0.5;
this->y = long double(y) + 0.5;
}
對於int
和人,它主要是無用的,但工程。對於浮點,我們使用更大的浮點類型以避免丟失精度,然後執行舍入。
顯然,如果我們突然想要一個Point<float>
,那就不太合適,因此我們需要一個基於類型特徵的更智能的解決方案。類std::numeric_limits<T>
有一個is_integer
,它降低了我們是否正在處理整數類型。
template <typename T>
template <typename Num>
void Point<T>::Set(Num x, Num y)
{
if (std::numeric_limits<T>::is_integer &&
!std::numeric_limits<Num>::is_integer)
{
this->x = x + 0.5;
this->y = y + 0.5;
}
else
{
this->x = x;
this->y = y;
}
}
}
我知道這似乎愚蠢使用的東西,可以在編譯時確定的if
......不過不用擔心,編譯器是足夠聰明,做數字出來編譯期時時間和優化掉if
和未使用的分支完全;)
我會專門浮動版本而不是所有的非浮動的一個:-) – AProgrammer 2011-02-26 17:55:40
@AProgrammer,在OP只提到希望專注於tPoint,但我同意他是否想要第二個「設置」多於一個班。 –
2011-02-26 18:05:57