Можно ли точно выполнить приведение в java без использования форматированного printf?

Эта строка приводит к двойному значению 3.33333333335

System.out.println("Average marks of " + name + " = " + (double)sum/3);

Можно ли установить ширину точности?


person drac_o    schedule 13.03.2020    source источник
comment
Отвечает ли это на ваш вопрос? printf %f только с двумя числами после запятой?   -  person Amongalen    schedule 13.03.2020
comment
это не литье. это отпечаток   -  person jhamon    schedule 13.03.2020
comment
Нет, точность фиксируется с помощью double. Вот почему вам нужно отформатировать его, если вы хотите другое представление.   -  person Kayaman    schedule 13.03.2020
comment
@Amongalen это возможно с методом printf, но мне было интересно, возможно ли это с помощью print   -  person drac_o    schedule 13.03.2020
comment
Это не. Это одна из причин существования printf, позволяющая форматировать вывод.   -  person Kayaman    schedule 13.03.2020


Ответы (3)


Вы можете использовать DecimalFormat или BigDecimal следующим образом:

import java.math.BigDecimal;
import java.math.RoundingMode;
import java.text.DecimalFormat;

public class Main {
    public static void main(String[] args) {
        int sum = 10;
        DecimalFormat decimalFormat = new DecimalFormat("#.##");
        System.out.println(Double.valueOf(decimalFormat.format((double) sum / 3)));

        // Another way
        System.out.println(new BigDecimal(String.valueOf((double) sum / 3)).setScale(2, RoundingMode.HALF_UP));

        // The better way using BigDecimal - thanks to @Andreas
        System.out.println(BigDecimal.valueOf(sum).divide(BigDecimal.valueOf(3), 2, RoundingMode.HALF_UP));
    }
}

Вывод:

3.33
3.33
3.33
person Arvind Kumar Avinash    schedule 13.03.2020
comment
Вместо потенциальной потери точности при переходе через double используйте BigDecimal.valueOf(sum).divide(BigDecimal.valueOf(3), 2, RoundingMode.HALF_UP). Теперь вы можете превысить точность double, например. с 25 десятичными знаками, в результате чего получается 3.3333333333333333333333333, где прохождение через double приведет к 3.3333333333333335000000000. - person Andreas; 13.03.2020

Распечатайте результат String.format(String, Object...) (то же самое, что printf с дополнительным шагом), или используйте BigDecimal (если вам нужен тип с произвольной точностью).

person Elliott Frisch    schedule 13.03.2020

Одним из решений является запись функции:

static double roundWithTwoDigits(double x) {
    return (double) Math.round(x * 100) / 100;
}

Теперь вы можете использовать его:

System.out.println("Average marks of " + name + " = " + roundWithTwoDigits((double) sum / 7));
person vbezhenar    schedule 13.03.2020
comment
Я не думаю, что это будет работать для действительно больших чисел, не так ли? - person Amongalen; 13.03.2020
comment
Да, для действительно больших чисел следует использовать BigDecimals. Это больше, чтобы ответить на вопрос, как получить двузначное точное число без форматирования. Это возможно, но оно определенно ограничено, и для форматирования следует использовать форматирование, а для контроля точности следует использовать BigDecimal. - person vbezhenar; 13.03.2020