Целочисленное подразделение: как вы производите двойной?

Для этого кода:

int num = 5;
int denom = 7;
double d = num / denom;

значение d равно 0.0. Его можно заставить работать путем кастинга:

double d = ((double) num) / denom;

Но есть ли другой способ получить правильный результат double? Мне не нравятся литые примитивы, кто знает, что может случиться.

Ответ 1

double num = 5;

Это позволяет избежать приведения. Но вы обнаружите, что преобразования конверсий четко определены. Вам не обязательно гадать, просто проверьте JLS. int double - это расширяющееся преобразование. Из §5.1.2:

Расширение примитивных преобразований не потерять информацию об общем величина числового значения.

[...]

Преобразование значения int или long плавать или иметь длинное значение для двойной, может привести к потере точность, то есть результат может потерять некоторые из наименее значимых бит Значение. В этом случае результат значение с плавающей запятой будет правильно округленная версия целочисленное значение, используя IEEE 754 круглый до ближайшего режима (§4.2.4).

5 может быть выражен точно как двойной.

Ответ 2

Что случилось с примитивами литья?

Если вы не хотите бросать по какой-то причине, вы можете сделать

double d = num * 1.0 / denom;

Ответ 3

Мне не нравятся приведения примитивов, кто знает, что может случиться.

Почему у вас есть иррациональный страх перед литью примитивов? Ничего плохого не произойдет, если вы нажмете int на double. Если вы просто не знаете, как это работает, посмотрите в Спецификация Java Language. Листинг int to double - это расширение примитивного преобразования.

Вы можете избавиться от дополнительной пары круглых скобок, выставив знаменатель вместо числителя:

double d = num / (double) denom;

Ответ 4

Если вы измените тип одного из переменных, которые вы должны запомнить, чтобы снова прокрасться в двойник, если ваша формула изменится, потому что если эта переменная перестает быть частью вычисления, результат будет испорчен. Я делаю привычку бросать в расчет и добавляю комментарий рядом с ним.

double d = 5 / (double) 20; //cast to double, to do floating point calculations

Обратите внимание, что выполнение результата не будет выполнено

double d = (double)(5 / 20); //produces 0.0

Ответ 5

Передайте одно из целых чисел/оба целого числа для float, чтобы заставить операцию выполнить с помощью математической математики с плавающей запятой. Иначе целочисленная математика всегда предпочтительна. Итак:

1. double d = (double)5 / 20;
2. double v = (double)5 / (double) 20;
3. double v = 5 / (double) 20;

Обратите внимание, что приведение результата не будет выполнено. Поскольку первое деление выполняется в соответствии с правилом приоритета.

double d = (double)(5 / 20); //produces 0.0

Я не думаю, что есть какие-то проблемы с кастингом, о котором вы думаете.

Ответ 6

Тип литья - единственный способ


Создание a double из целочисленного деления - нет другого пути без casting (возможно, вы не будете делать это явно, но это будет бывает).

Теперь мы можем попытаться получить точное значение double (где num и denom являются int и, конечно же, с кастингом) -

  • с явным литьем:

    • double d = (double) num / denom;
    • double d = ((double) num) / denom;
    • double d = num / (double) denom;
    • double d = (double) num / (double) denom;

но не double d = (double) (num / denom);

  1. с неявным литьем:

    • double d = num * 1.0 / denom;
    • double d = num / 1d / denom;
    • double d = ( num + 0.0 ) / denom;
    • double d = num; d /= denom;

но не double d = num / denom * 1.0;
и не double d = 0.0 + ( num / denom );

Ответ 7

используйте что-то вроде:

double step = 1d / 5;

(1d - это бросок, чтобы удвоить)

Ответ 8

Вы можете рассмотреть возможность переноса операций. Например:

class Utils
{
    public static double divide(int num, int denom) {
        return ((double) num) / denom;
    }
}

Это позволяет вам искать (только один раз), делает ли актер именно то, что вы хотите. Этот метод также может быть подвергнут испытаниям, чтобы он продолжал делать то, что вы хотите. Также не имеет значения, какой трюк вы используете для деления (вы можете использовать любой из ответов здесь), если это приводит к правильному результату. В любом месте вам нужно разделить два целых числа, теперь вы можете просто вызвать Utils::divide и верить, что он поступает правильно.

Ответ 9

просто используйте это.

int fxd=1;
double percent= (double)(fxd*40)/100;

Ответ 10

Лучший способ сделать это -

int i = 3;
Double d = i * 1.0;

d is 3.0 now.