Внутреннее представление числа в R

#r #precision

#r #точность

Вопрос:

 > trunc(26015)
[1] 26015
> 260.15*100
[1] 26015
> trunc(260.15*100)
[1] 26014
> floor(260.15*100)
[1] 26014
> as.integer(260.15*100)
[1] 26014
  

Для этого кода на R есть ли проблема с внутренним представлением числа?
Когда я делаю 260.15 * 100, печатаемое число по-прежнему равно 26015, но когда я использую функцию, такую как trunc() или as.integer() , оно становится 26014.
Обычно мое значение, содержащее десятичное число, берется из другой переменной. Итак, как мне преодолеть эту проблему?

Ответ №1:

Метод печати для числового не совпадает с его внутренним представлением. 260.15 * 100 на самом деле никогда не бывает 26015, оно просто печатается как таковое. print.numeric использует округление. Базовые numeric данные с плавающей запятой. Вы можете увидеть это, изменив параметры печати:

 # set print.numeric() to display up to 22 digits, the maximum possible
> options(digits = 22)
> 260.15 * 100
[1] 26014.99999999999636202
> 26015
[1] 26015

  

Вместо trunc() или as.integer() round() соответствует вашим потребностям?

Комментарии:

1. Спасибо за объяснение. Да, round() действительно дает мне правильное значение. Но нет ли способа сохранить 260.15 * 100 как сам 26015? Кроме того, это хранится непоследовательно? Потому что trunc(160.15 *100) сам выдает 16015. И использование round() для меня не вариант, поскольку я действительно хочу, чтобы усечение получало целое число. В некоторых случаях у меня есть десятичные значения, поэтому я не могу их округлить, а нужно просто их усечь.

2. 260.15 * 100 — это <26015 в арифметике с плавающей запятой. В этом нет несоответствия trunc() — некоторые числа немного выше или ниже. Это математика fp. trunc() является приблизительной десятичной операцией, реализованной для неточных чисел fp. R не имеет двоичного кодирования или точного десятичного типа данных — нецелая десятичная математика, отличная от fp, редко встречается в современных языках. Если вам нужно сохранить десятичные дроби в определенной фиксированной точке (например, центы для бухгалтерского учета), вы можете использовать целые числа и разделить на 100 в качестве последнего шага. В противном случае наилучший подход зависит от ваших конкретных потребностей. round() позволяет указать десятичные разряды.