Ce cas de test se termine assez explicite:
public static void main (String[] args) throws java.lang.Exception
{
System.out.println("Rounded: " + round(2.655d,2)); // -> 2.65
System.out.println("Rounded: " + round(1.655d,2)); // -> 1.66
}
public static Double round(Double d, int precise)
{
BigDecimal bigDecimal = new BigDecimal(d);
System.out.println("Before round: " + bigDecimal.toPlainString());
bigDecimal = bigDecimal.setScale(precise, RoundingMode.HALF_UP);
System.out.println("After round: " + bigDecimal.toPlainString());
return bigDecimal.doubleValue();
}
Sortie:
Before round: 2.654999999999999804600747665972448885440826416015625
After round: 2.65
Rounded: 2.65
Before round: 1.6550000000000000266453525910037569701671600341796875
After round: 1.66
Rounded: 1.66
Un sale hack pour corriger ce serait à tour en deux étapes:
static Double round(Double d, int precise)
{
BigDecimal bigDecimal = new BigDecimal(d);
System.out.println("Before round: " + bigDecimal.toPlainString());
bigDecimal = bigDecimal.setScale(15, RoundingMode.HALF_UP);
System.out.println("Hack round: " + bigDecimal.toPlainString());
bigDecimal = bigDecimal.setScale(precise, RoundingMode.HALF_UP);
System.out.println("After round: " + bigDecimal.toPlainString());
return bigDecimal.doubleValue();
}
Ici, 15
est un peu sous le nombre maximal de chiffres un double peut représenter dans la base 10. Sortie:
Before round: 2.654999999999999804600747665972448885440826416015625
Hack round: 2.655000000000000
After round: 2.66
Rounded: 2.66
Before round: 1.6550000000000000266453525910037569701671600341796875
Hack round: 1.655000000000000
After round: 1.66
Rounded: 1.66