153 votes

Cast en int vs floor

Y a-t-il une différence entre les deux ?

float foo1 = (int)(bar / 3.0);
float foo2 = floor(bar / 3.0);

Si je comprends bien, les deux cas ont le même résultat. Y a-t-il une différence dans le code compilé ?

1 votes

Un peu mieux avec floor mais attention, c'est pour double pas pour float . C99 a également floorf pour float .

3 votes

Ils ont donc le même résultat tant que la barre est positive.

1 votes

(note : en C++, veuillez #include<cmath> et utiliser std::floor )

247voto

James Curran Points 55356

Le transfert vers un int sera tronqué vers zéro. floor() sera tronqué vers l'infini négatif. Cela vous donnera des valeurs différentes si bar étaient négatifs.

17 votes

Je pense que vous avez mis le doigt sur le problème. Une autre différence, si floor() est l'intention, est si la valeur de bar est trop grande pour tenir dans un int .

0 votes

Avez-vous une source pour cette déclaration ?

2 votes

Même lorsque le résultat est positif, il n'est pas garanti. Voir este y este .

41voto

brice rebsamen Points 51

Comme il a été dit précédemment, pour les nombres positifs, ils sont les mêmes, mais ils diffèrent pour les nombres négatifs. La règle est que int arrondit vers 0, tandis que floor arrondit vers l'infini négatif.

floor(4.5) = (int)4.5 = 4
floor(-4.5) = -5 
(int)(-4.5) = -4

Ceci étant dit, il y a aussi une différence dans le temps d'exécution. Sur mon système, j'ai chronométré que le casting est au moins 3 fois plus rapide que le floor.

J'ai un code qui a besoin de l'opération plancher d'une gamme limitée de valeurs, y compris les nombres négatifs. Et cela doit être très efficace, donc nous utilisons la fonction suivante pour cela :

int int_floor(double x) 
{ 
    return (int)(x+100000) - 100000; 
}

Bien sûr, cela échouera pour les très grandes valeurs de x (vous rencontrerez des problèmes de débordement) et pour les valeurs négatives inférieures à -100000, etc. Mais j'ai constaté qu'elle est au moins 3 fois plus rapide que le plancher, ce qui était vraiment critique pour notre application. Prenez-le avec un grain de sel, testez-le sur votre système, etc. mais il vaut la peine d'être considéré IMHO.

0 votes

"J'ai mesuré qu'il est au moins 3 fois plus rapide que le sol" --> L'OP utilise float pas double - peut-être double était votre demande. Si vous êtes en C, assurez-vous d'utiliser floorf() con float s.

1 votes

@chux Je pense que la seule raison pour laquelle il y a une différence est que le cast permet une optimisation à la compilation. Donc cette conversion peut en fait avoir été complètement supprimée pendant l'exécution.

9voto

Claptrap Points 21299

SO 101, ne modifiez pas votre question après que des personnes y ont répondu, écrivez plutôt une nouvelle question.

Pourquoi pensez-vous qu'ils auront le même résultat ?

float foo = (int)(bar / 3.0) //will create an integer then assign it to a float

float foo = fabs(bar / 3.0 ) //will do the absolute value of a float division

bar = 1.0

foo1 = 0;
foo2 = 0.33333...

1 votes

Que voulez-vous dire par fabs ? La question portait sur floor . Le sol de 0.33333 ... est 0 .

4 votes

@AaronFranke la question originale a été modifiée. il semble que beaucoup de choses peuvent se passer en 8 ans ;-) remarquez que les autres réponses ont la même prémisse.

3voto

Amardeep Points 10417

EDIT : Parce que la question a pu être modifiée suite à une confusion entre fabs() y floor() .

Étant donné les lignes d'exemple de la question originale :

1.  float foo = (int)(bar / 3.0);

2.  float foo = fabs(bar / 3.0);

La différence est que si la barre est négative, le résultat sera négatif avec la première mais positif avec la seconde. La première sera tronquée en un nombre entier et la seconde renverra la valeur décimale complète, y compris la partie fractionnaire.

3voto

warrenm Points 10124

Oui. fabs renvoie la valeur absolue de son argument, et le cast en int provoque la troncature de la division (jusqu'à l'int le plus proche), donc les résultats seront presque toujours différents.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X