Я видел функцию double frexp (double x, int* exp);
, которая разбивает двойное значение на мантисса (m) и показатель степени (e) со степенью двойки (1.m * 2^e
). Есть ли аналогичная функция, которая возвращает значение в степени 10? Что-то вроде m * 10^e
было бы идеально.
Как получить мантиссу и показатель степени двойного числа в степени 10?
Ответы (1)
Дело в frexp
заключается в том, что если вы используете двоичные числа с плавающей запятой IEEE 754 (или PDP-11 с плавающей запятой), он просто показывает представление значения с плавающей запятой. Таким образом, разложение является точным и биективным: вы можете восстановить аргумент по полученным значениям и показателю степени.
Не существует эквивалентной причины для выделения функции разложения в десятую степень. На самом деле определение такой функции вызвало бы ряд технических трудностей: не все степени числа десять могут быть представлены в точности как double
: 0,1 и 1023 нет. Что касается десятичной значащей части, вам нужно значение, близкое к аргументу при умножении на 10e или приближение с двойной точностью 10e ? Некоторые значения с плавающей запятой могут иметь несколько одинаково допустимых разложений. Некоторые значения с плавающей запятой могут не иметь декомпозиции.
Если эти аспекты точности и каноничности не имеют для вас значения, используйте e = floor(log10(abs(x)))
для 10-кратной экспоненты (или ceil
для соглашения, более похожего на frexp
в стиле PDP-11) и x / pow(10, e)
для 10-значной мантиссы. Если для вас важно, чтобы значение мантиссы находилось в диапазоне от 1 до 10, вам лучше форсировать это свойство, зажав его.
ПРИМЕЧАНИЕ. Если вы хотите преобразовать x
в десятичное число, проблема заключается в глубоко изучен. Первым шагом правильного округления преобразования в десятичное является не вычисление десятичной мантиссы как числа с плавающей запятой (во всяком случае, не во всех случаях; для некоторых входных данных это может быть приемлемым сокращением), потому что в общем случае этот шаг привел бы к приближениям, недопустимым для корректно округленной функции преобразования. Для быстрого и грязного преобразования в десятичную процедуру (в случае, если у вас есть доступ к log10
, но нет к sprintf
), этого может быть достаточно.