Jak powiedziano wcześniej, dla liczb dodatnich są one takie same, ale różnią się dla liczb ujemnych. Zasada jest taka, że int zaokrągla się w kierunku 0, podczas gdy floor zaokrągla w kierunku ujemnej nieskończoności.
To powiedziawszy, istnieje również różnica w czasie wykonania. W moim systemie mierzyłem czas, że rzucanie jest co najmniej 3 razy szybsze niż podłoga.
Mam kod, który wymaga działania z ograniczonym zakresem wartości, w tym liczb ujemnych. I musi być bardzo wydajne, więc używamy do tego następującej funkcji:
int int_floor(double x){return(int)(x+100000)-100000;}
Oczywiście to się nie powiedzie dla bardzo dużych wartości x (napotkasz problemy z przepełnieniem) i dla wartości ujemnych poniżej -100000 itd. Ale taktowałem tak, aby był co najmniej 3 razy szybszy niż floor, co było naprawdę krytyczne dla naszej aplikacji. Weź to z przymrużeniem oka, przetestuj na swoim systemie itp., Ale warto rozważyć IMHO.
„Mam taktowanie, aby było co najmniej 3 razy szybsze niż podłoga” -> OP używa float, nie double- być może doublebyła to Twoja aplikacja. Jeśli w C, pamiętaj, aby użyć floorf()z floats.
@chux Myślę, że jedyną różnicą jest to, że rzutowanie pozwala na optymalizację w czasie kompilacji. Więc ta konwersja mogła zostać całkowicie usunięta podczas wykonywania.
SO 101, nie zmieniaj swojego pytania po tym, jak ludzie odpowiedzieli na Twoje pytanie, zamiast tego napisz nowe pytanie.
Jak myślisz, dlaczego będą miały ten sam wynik?
float foo =(int)(bar /3.0)//will create an integer then assign it to a floatfloat foo = fabs(bar /3.0)//will do the absolute value of a float division
bar =1.0
foo1 =0;
foo2 =0.33333...
@AaronFranke oryginalne pytanie zostało zmodyfikowane. wydaje się, że wiele może się wydarzyć w ciągu 8 lat ;-) zauważ, że inne odpowiedzi mają to samo założenie
Różnica polega na tym, że jeśli słupek jest ujemny, wynik będzie ujemny z pierwszym, ale dodatni z drugim. Pierwsza zostanie obcięta do liczby całkowitej, a druga zwróci pełną wartość dziesiętną, w tym część ułamkową.
Tak. fabszwraca wartość bezwzględną swojego argumentu, a rzutowanie na wartość int powoduje obcięcie dzielenia (w dół do najbliższej liczby całkowitej), więc wyniki będą prawie zawsze inne.
Jak inni zauważyli, rzutowanie na liczbę całkowitą będzie skracane do zera, podczas gdy floor()zawsze będzie obcięte w kierunku ujemnej nieskończoności; jest to inne zachowanie dla argumentu ujemnego.
Wydaje się, że nikt (jeszcze) nie zwrócił uwagi na inną różnicę - jeśli argument jest większy lub równy MAX_INT+1(lub mniejszy niż -MAX_INT-1), rzutowanie na a intspowoduje odrzucenie najwyższych bitów (prawdopodobnie C) lub niezdefiniowane zachowanie ( C ++ i prawdopodobnie C). Na przykład, jeśli masz int32 bity, będziesz mieć tylko bit znaku plus 31 bitów danych. Więc użycie tego z doubledużym rozmiarem da niezamierzone rezultaty.
2.a. Dokładnym warunkiem konwersji na intprzepełnienie jest to, że argument jest większy lub równy INT_MAX+1. Symetrycznie warunkiem niedomiaru jest to, że argument jest mniejszy lub równy INT_MIN-1.
2.b. Przepełnienie konwersji ze zmiennoprzecinkowej na liczbę całkowitą jest niezdefiniowanym zachowaniem w C ++. Nie powoduje „odrzucenia największej liczby bitów”. Zobacz (chociaż jest napisane dla C): blog.frama-c.com/index.php?post/2013/10/09/…
Używamy plików cookie i innych technologii śledzenia w celu poprawy komfortu przeglądania naszej witryny, aby wyświetlać spersonalizowane treści i ukierunkowane reklamy, analizować ruch w naszej witrynie, i zrozumieć, skąd pochodzą nasi goście.
Kontynuując, wyrażasz zgodę na korzystanie z plików cookie i innych technologii śledzenia oraz potwierdzasz, że masz co najmniej 16 lat lub zgodę rodzica lub opiekuna.
floor, ale uważaj, todoublenie jest dlafloat. C99 ma równieżfloorfdlafloat.