既然比較floats是邪惡的,那么如果我有一個floats的容器,并且我使用一些標準庫的排序演算法如std::sort進行排序,那么該演算法是如何對它們進行排序的?
std::vector<float> vf{2. 4f, 1.05f, 1.05f, 2.39f};
std::sort( vf.begin(), vf.end( ) 。)
那么該演算法是否對
1.05f和1.05f進行了比較?它內部是否使用了類似的東西。
?std::fabs( 1.05f - 1.05f ) < 0.1;?這是否也適用于
doubles的容器?謝謝你!
uj5u.com熱心網友回復:
那么,該演算法是否對
1.05f和1.05f進行比較?
是的
它內部是否使用了類似的東西。
std::fabs( 1.05f - 1.05f ) < 0.1;?
不,它使用operator <,例如:1.05f < 1.05f。它不需要進行平等的比較,所以不需要使用epsilon值進行比較。
這是否也適用于doubles的容器?
是的,它適用于任何型別的容器(除非你為std::sort提供你自己的比較函式)
uj5u.com熱心網友回復:
既然比較
floats是邪惡的...
這是一個神話,是錯誤的。與此相關的是浮點數與實數相近的神話。
<, <=, >, 和>=對于數字的排序作業很好,而且==和!=也能正確比較兩個數字是否相等。<、<=、>和>=在對包含NaNs("非數字 "資料)的資料進行排序時將無法使用。
根據IEEE 754浮點運算標準和其他常見的浮點格式規范,任何浮點表示±F-be完全代表一個數字。甚至 ∞和-∞也被認為是精確的。是浮點運算中的操作,而不是數字,被指定為近似實數運算。當一個計算操作被執行時,其結果是根據選定的舍入規則將實數結果舍入到最接近的可表示的數字,但有域錯誤的操作可能產生NaN。("四舍五入 "是最常見的規則,還有一些其他的規則。)
因此,當你在進行四舍五入操作時,你會發現你的結果是最接近的。
因此,當你進行數字加減、數字乘除、取平方根或將數字從一個基數轉換為另一個基數(例如將十進制字符輸入為內部浮點格式)時,可能會出現舍入錯誤。
有些操作沒有錯誤。比較操作沒有錯誤。<, <=, >, >=, ==, 和!=總是產生真實的數學結果,真或假,沒有錯誤。因此,它們可以用于數字的排序。(對于NaN,它們總是產生false,因為NaN永遠不會小于、等于或大于一個數字,NaN也不會小于、等于或大于一個NaN。所以false是正確的結果,但這意味著這些比較對于用NaN進行排序是沒有用的。
理解這一區別,即數字是精確的,而操作可能是近似的,這對于分析、設計和證明涉及浮點運算的演算法至關重要。
當然,在一個數字陣列中,可能會出現數字包含早期操作的錯誤。它們與使用實數運算得到的數字不同。在這種情況下,這些數字將根據它們的實際計算值被排序,而不是根據你希望它們具有的理想值。這并不妨礙std::sort對數字進行正確排序。
為了對包括NaN在內的資料進行排序,您需要一個總的順序謂詞來報告一個資料在所需的排序順序中是否早于另一個資料,例如報告一個NaN是否晚于任何非NaN。IEEE-754定義了一個總順序謂詞,但我不能說它在C 中的可用性。(std::less似乎沒有提供它,基于我嘗試的快速測驗。)
轉載請註明出處,本文鏈接:https://www.uj5u.com/net/328373.html
標籤:
