Question

J'ai = double valeur 1.068879335 je veux arrondir avec seulement deux valeurs décimales comme 1,07.

J'ai essayé comme ceci

DecimalFormat df=new DecimalFormat("0.00");
String formate = df.format(value);
double finalValue = Double.parseDouble(formate) ;

me donne cette exception suivante

java.lang.NumberFormatException: For input string: "1,07"
     at sun.misc.FloatingDecimal.readJavaFormatString(FloatingDecimal.java:1224)
     at java.lang.Double.parseDouble(Double.java:510)

Quelqu'un peut me dire ce qui ne va pas avec mon code.

i besoin du finaly valeurFinale = 1.07;

Était-ce utile?

La solution

Notez la virgule dans votre chaîne: « 1,07 ». DecimalFormat utilise une chaîne de séparation spécifique à la localisation, alors que Double.parseDouble() ne fonctionne pas. Comme vous arrive de vivre dans un pays où le séparateur décimal est « », vous ne pouvez pas analyser votre dos numérique.

Cependant, vous pouvez utiliser le même DecimalFormat pour analyser en arrière:

DecimalFormat df=new DecimalFormat("0.00");
String formate = df.format(value); 
double finalValue = (Double)df.parse(formate) ;

Mais vous devriez vraiment faire ceci:

double finalValue = Math.round( value * 100.0 ) / 100.0;

Remarque: Comme il a été souligné, vous ne devez utiliser la virgule flottante si vous n'avez pas besoin d'un contrôle précis sur la précision. (Calculs financiers étant l'exemple principal lorsque pas pour les utiliser.)

Autres conseils

Live @ solution de Sergey mais avec la division entière.

double value = 23.8764367843;
double rounded = (double) Math.round(value * 100) / 100;
System.out.println(value +" rounded is "+ rounded);

impressions

23.8764367843 rounded is 23.88

EDIT: Comme Sergey souligne, il devrait y avoir aucune différence entre multipling double * int et double * double et division à double / int et double / double. Je ne peux pas trouver un exemple où le résultat est différent. Cependant sur x86 / x64 et d'autres systèmes, il existe une instruction de code machine spécifique pour double mixte, les valeurs int que je crois que les utilisations JVM.

for (int j = 0; j < 11; j++) {
    long start = System.nanoTime();
    for (double i = 1; i < 1e6; i *= 1.0000001) {
        double rounded = (double) Math.round(i * 100) / 100;
    }
    long time = System.nanoTime() - start;
    System.out.printf("double,int operations %,d%n", time);
}
for (int j = 0; j < 11; j++) {
    long start = System.nanoTime();
    for (double i = 1; i < 1e6; i *= 1.0000001) {
        double rounded = (double) Math.round(i * 100.0) / 100.0;
    }
    long time = System.nanoTime() - start;
    System.out.printf("double,double operations %,d%n", time);
}

Prints

double,int operations 613,552,212
double,int operations 661,823,569
double,int operations 659,398,960
double,int operations 659,343,506
double,int operations 653,851,816
double,int operations 645,317,212
double,int operations 647,765,219
double,int operations 655,101,137
double,int operations 657,407,715
double,int operations 654,858,858
double,int operations 648,702,279
double,double operations 1,178,561,102
double,double operations 1,187,694,386
double,double operations 1,184,338,024
double,double operations 1,178,556,353
double,double operations 1,176,622,937
double,double operations 1,169,324,313
double,double operations 1,173,162,162
double,double operations 1,169,027,348
double,double operations 1,175,080,353
double,double operations 1,182,830,988
double,double operations 1,185,028,544

Le problème est que vous utilisez un localisant qui génère formatter point décimal locale spécifique, ce qui est « » dans votre cas. Mais Double.parseDouble () attend double non-localisée littérale. Vous pouvez résoudre votre problème en utilisant une méthode spécifique à l'analyse locale ou en changeant locale de votre formatter à quelque chose que les utilisations « » que le point décimal. Ou mieux encore, d'éviter le formatage inutile en utilisant quelque chose comme ceci:

double rounded = (double) Math.round(value * 100.0) / 100.0;

Il y a quelque chose de fondamentalement mauvais dans ce que vous essayez de faire. Binary-points flottants valeurs ne le font pas Vous décimales. Vous ne pouvez pas une façon significative autour d'un nombre donné de décimales, parce que la plupart des valeurs décimales « rondes » simplement ne peut pas être représenté sous la forme d'une fraction binaire. Quelle est la raison pour laquelle on ne devrait jamais utiliser float ou double pour représenter l'argent.

Donc, si vous voulez décimales dans le résultat, ce résultat doit être soit un String (que vous avez déjà obtenu avec le DecimalFormat), ou un BigDecimal (qui a une méthode setScale() qui fait exactement ce que vous voulez). Dans le cas contraire, le résultat ne peut pas être ce que vous voulez qu'il soit.

Lire Le guide-virgule flottante pour plus d'informations.

Essayez ceci: org.apache.commons.math3.util.Precision.round (double x, échelle int)

Voir: http: //commons.apache .org / bon / commons-math / apidocs / org / apache / communes / math3 / util / Precision.html

Apache Commons Mathématiques Accueil Library est: http://commons.apache.org/proper/commons-math/index.html

Implémentation interne de cette méthode est la suivante:

public static double round(double x, int scale) {
    return round(x, scale, BigDecimal.ROUND_HALF_UP);
}

public static double round(double x, int scale, int roundingMethod) {
    try {
        return (new BigDecimal
               (Double.toString(x))
               .setScale(scale, roundingMethod))
               .doubleValue();
    } catch (NumberFormatException ex) {
        if (Double.isInfinite(x)) {
            return x;
        } else {
            return Double.NaN;
        }
    }
}

Vous pouvez essayer de définir une nouvelle DecimalFormat et l'utiliser comme un double résultat à une nouvelle variable double.

Exemple donné pour vous faire comprendre ce que je viens de dire.

double decimalnumber = 100.2397;
DecimalFormat dnf = new DecimalFormat( "#,###,###,##0.00" );
double roundednumber = new Double(dnf.format(decimalnumber)).doubleValue();

Ce n'est pas possible de la manière demandée en raison du nombre avec deux décimales qui ne peuvent être exprimées exactement en utilisant des nombres à virgule flottante IEEE (par exemple 1/10 = 0,1 ne peut être exprimée en Double ou Float). La mise en forme doit toujours se produire comme la dernière étape avant de présenter le résultat à l'utilisateur.

Je suppose que vous demandez parce que vous voulez traiter avec des valeurs monétaires. Il n'y a aucun moyen de le faire de manière fiable avec des nombres à virgule flottante, vous shoud envisager de passer à Arithmétique à virgule fixe. Cela signifie probablement faire tous les calculs en « cents » au lieu de « dollars ».

double TotalPrice=90.98989898898;

  DecimalFormat format_2Places = new DecimalFormat("0.00");

    TotalPrice = Double.valueOf(format_2Places.format(TotalPrice));

Vous pouvez utiliser le format comme ici ,

  public static double getDoubleValue(String value,int digit){
    if(value==null){
        value="0";
     }
    double i=0;
     try {
         DecimalFormat digitformat = new DecimalFormat("#.##");
         digitformat.setMaximumFractionDigits(digit);
        return Double.valueOf(digitformat.format(Double.parseDouble(value)));

    } catch (NumberFormatException numberFormatExp) {
        return i;   
    }
}

Si vous ne souhaitez pas utiliser DecimalFormat (par exemple en raison de son efficacité) et que vous voulez une solution générale, vous pouvez aussi essayer cette méthode qui utilise l'échelle d'arrondi:

public static double roundToDigits(double value, int digitCount) {
    if (digitCount < 0)
        throw new IllegalArgumentException("Digit count must be positive for rounding!");

    double factor = Math.pow(10, digitCount);
    return (double)(Math.round(value * factor)) / factor;
}
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top