Изучаем округление в Java: как в Java округлить число до n знаков после запятой
Округление в Java: обзор
В этой статье мы рассмотрим, как в Java округлить число до n десятичного знаков.
Десятичные числа в Java
Java предоставляет два примитивных типа, которые могут использоваться для хранения десятичных чисел: float и double. Double - это тип данных, используемый по умолчанию:
double PI = 3.1415
Но оба типа данных не должны использоваться для вычисления точных значений. Например, валютных котировок и округления чисел. Для этого лучше применять класс BigDecimal.
Форматирование десятичного числа
Если нужно вывести десятичное число с n знаками после запятой, можно отформатировать выходную строку:
System.out.printf("Value with 3 digits after decimal point %.3f %n", PI);
// Вывод: Значения с 3 знаками после запятой 3.142
Также можно округлить значение с помощью класса DecimalFormat:
DecimalFormat df = new DecimalFormat("###.###");
System.out.println(df.format(PI));
Этот класс позволяет настроить процесс округления числа.
Java: округление Double с помощью BigDecimal
Чтобы округлить тип double до n знаков после запятой, можно написать helper-метод:
private static double round(double value, int places) {
if (places < 0) throw new IllegalArgumentException();
BigDecimal bd = new BigDecimal(Double.toString(value));
bd = bd.setScale(places, RoundingMode.HALF_UP);
return bd.doubleValue();
}
Обратите внимание, что при создании экземпляра класса BigDecimal мы должны всегда использовать конструктор BigDecimal(String). Это позволяет избежать проблем с представлением неточных значений.
Можно сделать то же самое, используя библиотеку Apache Commons Math:
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-math3</artifactId>
<version>3.5</version>
</dependency>
Актуальную версию этой библиотеки можно найти здесь. Для округления чисел применяется метод Precision.round() , который принимает два аргумента - значение и масштаб:
Precision.round(PI, 3);
По умолчанию он использует тот же метод округления HALF_UP, что хэлпер. Поэтому результаты должны быть одинаковыми.
Кроме этого можно изменить процесс приведения чисел, передав в качестве третьего параметра необходимый метод округления.
Округление чисел с плавающей запятой с помощью DoubleRounder
DoubleRounder - это утилита из библиотеки decimal4j. Она предоставляет быстрый метод округления double чисел до 18 знаков после запятой.
Последнюю версию библиотеки можно найти здесь. Чтобы подключить ее, добавьте зависимость в файл pom.xml:
<dependency>
<groupId>org.decimal4j</groupId>
<artifactId>decimal4j</artifactId>
<version>1.0.3</version>
</dependency>
Пример использования утилиты:
DoubleRounder.round(PI, 3);
Но DoubleRounder дает сбой в нескольких сценариях. Например:
System.out.println(DoubleRounder.round(256.025d, 2));
// OUTPUTS: 256.02 вместо ожидаемого 256.03
Метод Math.round() java
При использовании метода Math.round() можно контролировать п-количество десятичных разрядов путем умножения и деления на 10^п :
public static double roundAvoid(double value, int places) {
double scale = Math.pow(10, places);
return Math.round(value * scale) / scale;
}
Этот метод не рекомендуется использовать для округления чисел, поскольку он усекает значение. Во многих случаях значения округляются неправильно:
System.out.println(roundAvoid(1000.0d, 17));
// Вывод: 92.23372036854776 !!
System.out.println(roundAvoid(260.775d, 2));
// Вывод: 260.77 вместо ожидаемого 260.78
Заключение
В этой статье мы рассмотрели различные методы округления чисел до n знаков после запятой, доступные в Java.
Можно просто отформатировать вывод без изменения значения или округлить переменную с помощью вспомогательного метода или подключаемых библиотек.
Код, использованный в этой статье, доступен на GitHub.