Nie ma żadnego historycznego powodu. Ten rodzaj dewiacji istnieje od roku Dot. Ludzie robią to, gdy czują się bardzo, bardzo niegrzeczni. Jest to nadużycie arytmetyki zmiennoprzecinkowej i wielu doświadczonych zawodowych programistów się na to daje. Nawet elementy Java działały do wersji 1.7. Śmieszni goście.
Moje przypuszczenie jest takie, że przyzwoita, gotowa do użycia, niemiecka funkcja zaokrąglania nie była formalnie dostępna aż do C ++ 11 (pomimo, że C dostał swoje w C99), ale to naprawdę nie jest wymówką dla przyjęcia tak zwanej alternatywy.
Oto rzecz: floor(0.5 + input)
nie zawsze odzyskuje ten sam wynik, co odpowiednie std::round
połączenie!
Powód jest dość subtelny: punkt odcięcia dla zaokrąglenia niemieckiego a.5
dla liczby całkowitej a
jest, przez przypadkową właściwość Wszechświata, diadą racjonalną . Ponieważ można to dokładnie przedstawić w zmiennoprzecinkowym IEEE754 do 52 potęgi 2, a następnie zaokrąglanie jest i tak nie std::round
działa , zawsze działa poprawnie. W przypadku innych schematów zmiennoprzecinkowych zapoznaj się z dokumentacją.
Ale dodanie 0.5
do a double
może wprowadzić niedokładność, powodując niewielkie niedokonanie lub przeregulowanie dla niektórych wartości. Jeśli się nad tym zastanowić, dodanie do siebie dwóch double
wartości - które są początkiem nieświadomych konwersji denarów - i zastosowanie funkcji, która jest bardzo silną funkcją danych wejściowych (na przykład funkcja zaokrąglania), z pewnością zakończy się łzami.
Nie rób tego .
Odniesienie: Dlaczego Math.round (0.49999999999999994) zwraca 1?