2010-11-21 6 views

Répondre

11

Toutes les opérations sont effectuées sur des objets de du même type (en supposant des opérations arithmétiques normales).

Si vous écrivez un programme qui utilise différents types, le compilateur mettra automatiquement à jour le paramètre ONE afin qu'ils soient identiques.

Dans ce cas flotteurs seront modernisés à double:

result  = a * (b + c) * d 

float tmp1 = b + c;   // Plus operation done on floats. 
           // So the result is a float 

double tmp2 = a * (double)tmp1; // Multiplication done on double (as `a` is double) 
           // so tmp1 will be up converted to a double. 

double tmp3 = tmp2 * d;   // Multiplication done on doubles. 
           // So result is a double 

result  = tmp3;    // No conversion as tmp3 is same type as result. 
+0

noter également des constantes non spécifiées sont supposées être double donc float a; a = a + 2,5; va convertir un pour doubler, exécutez l'addition puis revenez en simple: a = a + 2.5F; le forcerait à tous les calculs simples –

3

Si vous avez:

float f; 
double d; 

... alors une expression arithmétique comme f * d promouvra les deux opérandes du type plus grand, qui dans ce cas est double.

Ainsi, l'expression a * (b + c) * d renvoie une double et est ensuite stocké dans result, qui est aussi un double. Ce type de promotion est effectué afin d'éviter une perte de précision accidentelle.

Pour plus d'informations, lisez cet article à propos de l'habituel arithmetic conversions.

+3

Mais les deux opérandes à plus sont flottants. Donc le plus sera fait en utilisant float dont le résultat sera mis à jour en double avant que l'opération de multiplication ne soit faite. –

0

Les flotteurs seront convertis en double. Transmettre explicitement les valeurs.

à savoir si vous voulez que votre résultat à double vous écrire:

Il est toujours la peine d'être explicite. Il obtient des malentendus comme celui-ci et il est immédiatement évident pour quiconque essaie d'utiliser votre code exactement ce que vous voulez dire.

+0

Ce n'est pas correct. Dans l'expression originale, ni b ', ni 'c' ne seront pas promus en double, ils seront ajoutés comme deux' float's. Le résultat sera promu à un «double» seulement lorsqu'il est multiplié avec quelque chose qui est déjà un «double», c'est-à-dire «a». –

+0

C'est faux. :-( –

+0

@Charles: sacrément vous avez raison.Fixe – Goz

0

Vous avez des parenthèses délimitant l'adition flottante. Donc, il ferait b + c comme float + float. Convertissez ceci en double pour garder la plus grande précision, puis multipliez les valeurs doubles.

Toutefois, si vous souhaitez contrôler les conversions et ne pas deviner: , utilisez static_cast<>();

1

Après ordre des opérations, chaque sous-expression est convertie au type de son type (pas sûr du terme ici, dominante peut-être?) . deux est dominant sur float, donc:

(b + c) // this is evaluated as a float, since both b and c are floats 
a * (b + c) // this is evaluated as a double, since a is a double 
a * (b + c) * d // this is evaluated as a double, since both "a * (b + c)" and d are doubles 
0

Dans votre exemple, tous les types float sont de type promu double lorsque la formule du côté droit est évaluée.En ce qui concerne les opérations en virgule flottante, j'ai constaté que la plupart des équipements contemporains effectuent des opérations de FP en utilisant des doubles longs de précision étendue (80 bits) dans des registres matériels spéciaux (du moins c'est ce dont je me souviens à propos des processeurs Intel x86/x87 modernes). Si je comprends bien, float et double sont HARDWARE promu par type via des instructions spéciales de FP (quelqu'un me corrige si je me trompe).

+1

Ceci n'est pas correct. Les 'float' ne sont pas automatiquement promus en' double'. «double» s'ils apparaissent dans une opération arithmétique avec quelque chose qui est déjà «double» Dans ce cas, ni «b» ni «c» ne seront convertis en «double» avant l'addition. –

1

Vous devez faire la différence entre la conversion de type et la conversion de valeur. Le standard C++ (C également) permet de faire des calculs en virgule flottante avec une précision étendue. "Les valeurs des opérandes flottants et les résultats des expressions flottantes peuvent être représentés avec une plus grande précision et une plus grande plage que celle requise par le type, les types ne sont pas modifiés de cette manière." Comme types, b + c est une addition de deux flotteurs. Le résultat est un flotteur. Le résultat est ensuite promu en double et les deux multiplications sont effectuées en double avec un résultat de double. Cependant, une implémentation est autorisée à faire tous les calculs, y compris b + c, en utilisant des doubles (ou une précision plus élevée). En effet, je l'ai essayé en utilisant Visual C++ et il a fait tous les calculs en utilisant la pile à virgule flottante de 80 bits disponible sur x86.

Questions connexes