2012-03-29 5 views
7

In C#, sto cercando di ottenere gli ultimi due decimali di un doppio senza arrotondamento. Ho provato tutto da Math.Floor a Math.Truncate e non funziona nulla.Ottieni ultime 2 cifre decimali senza arrotondamento

Campioni dei risultati mi piacerebbe:

1,424.2488298 -> 1,424.24 
53.5821 -> 53.58 
10,209.2991 -> 10,209.29 

Tutte le idee?

+1

Se sei facendo il lavoro in * decimale *, allora perché stai usando * double * quando potresti usare * decimal *? –

+0

Puoi andare a questo post e trovare quello che ti si adatta. Http://how-to-code-net.blogspot.ro/2012/09/how-to-format-number-to-x-decimal.html –

risposta

22

Beh, matematicamente è semplice:

var f = 1.1234; 
f = Math.Truncate(f * 100)/100; // f == 1.12 

Spostare i decimali due posti a destra, espressi ad un int per troncare, spostare di nuovo a sinistra due posti. Ci possono essere modi nel quadro di farlo anche, ma non posso guardare in questo momento. Si potrebbe generalizzare:

double Truncate(double value, int places) 
{ 
    // not sure if you care to handle negative numbers...  
    var f = Math.Pow(10, places); 
    return Math.Truncate(value * f)/f; 
} 
+0

Non così semplice I doppi hanno una portata maggiore rispetto agli int. – Joe

+0

@joe: Ahh, buon punto, usa Math.Truncate invece, nessuna cast richiesta –

+0

@EdS. Ho provato questo sul valore 136.2025 usando il tuo primo metodo e lo ha tagliato a 136.2 e lasciato cadere lo 0. C'è un modo per mantenere lo 0 in esso? – mint

5
double d = Math.Truncate(d * 100)/100; 
2

una soluzione generale:

public static double SignificantTruncate(double num, int significantDigits) 
    { 
     double y = Math.Pow(10, significantDigits); 
     return Math.Truncate(num * y)/y; 
    } 

Poi

double x = 5.3456; 
    x = SignificantTruncate(x,2); 

produrrà il risultato desiderato x=5.34.

14

Il mio consiglio: smettere di usare double in primo luogo. Se hai bisogno di arrotondamento decimale, allora le probabilità sono buone, dovresti usare decimal. Qual è la tua applicazione?

Se si dispone di un doppio, si può fare in questo modo:

double r = whatever; 
decimal d = (decimal)r; 
decimal truncated = decimal.Truncate(d * 100m)/100m; 

Si noti che questa tecnica non riesce se il valore assoluto del doppio è più grande di 792281625142643375935439504, perché la moltiplicazione per 100 fallirà . Se devi gestire valori così grandi, dovrai utilizzare tecniche speciali. (Naturalmente, per il momento in una doppia è che di grandi dimensioni, si sono ben oltre la sua capacità di rappresentare i valori con due cifre dopo il decimale in ogni caso.)

2
Math.Round(NumberToRound - (double)0.005,2) 

cioè

Math.Round(53.5821 - (double)0.005,2) // 53.58 
Math.Round(53.5899 - (double)0.005,2) // 53.58 
Math.Round(53.5800 - (double)0.005,2) // 53.58