2013-10-29 56 views
1

在用作模板放慢參數的一類的成員函數,我有包含以下代碼的函數:奇怪靜態鑄造行爲用作模板參數

double x = /*Something operation returning double*/; 
x /= CubeWidth; /*CubeWidth is a class member*/ 
cout << "Element after centering and normalization = " << x << endl; 
cout << "and after adding 1 and truncating = " << x+1 << endl; 
cout << "then static cast = " << (int) x+1 << endl; 

這樣做的輸出功能

Element after centering and normalization = 1 
and after adding 1 and truncating = 2 
then static cast = 1 

很明顯,最後一行應該給出一個答案2.

如果我實例完全相同的類不使用它作爲模板參數,我不要得到這個打印輸出,而是我有正確的。

有誰能告訴我爲什麼會發生這種情況?

+2

好問題爲什麼。我知道如何解決這個問題,但是 - 把你的表達式放在括號裏。例如'((int)x + 1)'。我也會等待好的解釋。編輯:如果這個解決方案不起作用,那麼我*必須是Daniel Frey寫的。 – Grzegorz

+2

@j_random_hacker Nope,'+'的優先級高於'<<'的優先級,請參見[here](http://en.cppreference.com/w/cpp/language/operator_precedence)。 –

+0

@j_random_hacker:'1 << 2 + 1'確實是'1 << 3',例如'8',而不是'3'。 「... <<(cond)」的優先順序是有意義的嗎? x:y << ...在這種情況下代替'y',表達式將使用'y << ...'。 – Grzegorz

回答

3

最有可能的x(雙)不完全是1,它是0.9999999...。通過打印x==1.0x<1.0來查看確切的值,並查看確實如此。或添加更多位數的輸出:

cout << "and after adding 1 and truncating = " << setprecision(15) << x+1 << endl; 

整數逗號後會扔掉所有的數字取整,因此1.999999...變得1

+0

我認爲你是對的,但效果已經開始隨機出現。我只是再次運行測試,沒有任何改變,除了我不再連接到無線網絡!這可能是相關的嗎?我知道我在抓秸稈...... – Plamen

+2

@Plamen宇宙射線,「相對Mondfeuchtigkeit」,...... - 但最終它更可能是'x'的計算,你沒有顯示。無論如何,只要讓你的代碼更安全,增加更多的數字或允許一個小的三角洲,例如'(INT)(X + 1.000001)'。也許[這個頁面](http://floating-point-gui.de)會有幫助。 –