2009-10-30 41 views
5

Estaba buscando la convención de redondeo utilizada por la función incorporada de Perl sprintf.¿Por qué el sprintf de Perl no redondea correctamente los números de coma flotante?

estaba pensando que lo hace un redondeo normal (por ejemplo ROUND_HALF_UP como en Java's rounding mode convention), pero excavación resultó más que esto sea malo:

> /usr/local/bin/perl5.10.1 -e 'print(sprintf("%.2f", shift @ARGV)."\n");' 0.335 
0.34 
> /usr/local/bin/perl5.10.1 -e 'print(sprintf("%.2f", shift @ARGV)."\n");' 1.335 
1.33 
+7

print (sprintf (...))? Me pregunto si hay un "printf" ... – jrockway

+1

Eche un vistazo a la [receta Perl Cookbook 2.2 - redondeando números de punto flotante] (http://books.google.com/books?id=hP4IRp8xwTkC&pg=PA64&lpg=PA64&dq= redondeo + números + Perl + libro de cocina y fuente = BL & ots = ti7Tyxr3s7 y sig = gyWX-iySyiVZef0vB43ZuIaxkuw & hl = es & ei = RPzrStmzO4z0MarIvKkI & SA = X & oi = book_result y ct = resultar y resnum = 1 & ved = 0CAwQ6AEwAA # v = OnePage y q = & f = false) para una explicación más completa – heferav

Respuesta

16

Usted ha sido mordido por el hecho de que los números de punto flotante no son representaciones exactas de fracciones decimales. Esto es lo que sale:

DB<1> $a=0.335 

    DB<5> print sprintf("%.19f",$a) 
0.3350000000000000200 
    DB<7> $b=1.335 

    DB<8> print sprintf("%.19f",$b) 
1.3349999999999999645 
    DB<9> 

Desde 0.335 se representa internamente como un poco mayor que 0,335 se redondea a 0,34, mientras que 1.335 es ligeramente inferior a 1.335, por lo que se redondea a 1,33.

Cuestiones relacionadas