Подтвердить что ты не робот

Легкий способ поиска знаков после запятой

Есть ли простой способ или интегрированная функция для поиска десятичных знаков числа с плавающей запятой?

Число анализируется из строки, поэтому одним из способов является подсчет цифр после ".". но это выглядит довольно неуклюжим для меня. Есть ли возможность получить необходимую информацию из объекта float или Decimal?

РЕШЕНИЕ (один из них, конечно:))

Я решил использовать десятичный класс python.Decimal, чтобы помочь мне с моей проблемой:

e = abs(Decimal(string_value).as_tuple().exponent)

ПРИМЕЧАНИЕ: это работает только тогда, когда параметр, из которого построена десятичная матрица, является строкой, а не плавающей точкой (что приведет к неточностям с плавающей запятой).

Большое спасибо за все остальные вклады.

4b9b3361

Ответ 1

Повторить то, что говорили другие (потому что я уже набрал его!), я даже не уверен, что такое значение имеет смысл в случае числа с плавающей запятой из-за разницы между десятичным и двоичным представление; часто число, представимое конечным числом десятичных цифр, будет иметь только двоичное представление с бесконечной цифрой.

В случае объекта decimal.Decimal вы можете получить показатель экспоненты с помощью метода as_tuple, который возвращает именованный элемент с атрибутами sign, digits и exponent:

>>> d = decimal.Decimal('56.4325')
>>> d.as_tuple().exponent
-4
>>> d = decimal.Decimal('56.43256436')
>>> d.as_tuple().exponent
-8

Отрицание экспоненты - это число цифр после десятичной точки, если показатель не превышает 0.

Ответ 2

"число десятичных знаков" на самом деле не является свойством числа с плавающей запятой из-за того, как они хранятся и обрабатываются внутри страны. Вы можете получить столько знаков после запятой, сколько хотите, из числа с плавающей запятой. Вопрос в том, насколько точно вы хотите. При преобразовании числа с плавающей запятой в строку часть процесса принимает решение о точности.

Попробуйте, например:

1.1 - int(1.1)

И вы увидите, что ответ:

0.10000000000000009

Итак, для этого случая число десятичных знаков равно 17. Это номер, который вы хотите?

Возможно, нет.

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

round(3.1415 - int(3.1415), 3)

В этом случае число десятичных знаков разрезается на 3.

Вы не можете получить "число десятичных знаков из поплавка", но вы можете определить точность и сколько хотите. Преобразование float в строку является одним из способов принятия такого решения.

Ответ 3

Наивный способ (уязвимый для локального использования, упомянутый @jglouie) - это

len(foo.split('.')[1])

где foo - строка типа "23.512999238".

ИЗМЕНИТЬ

Как отметил @Thomas Jung и @Mark Ransom, это довольно наивно для некоторых угловых случаев, которые нужно обрабатывать как...

import re
from locale import localeconv
dec_pt = localeconv()['decimal_point']
decrgx = re.compile("\d+(%s\d+)?e(-|\+)(\d+)" % dec_pt)
if decrgx.search(foo):
    # still figuring this out
    raise NotImplementedError, "e notation not implemented"
else:
    digits = len(foo.split(dec_pt)[-1])

Ответ 4

Десятичная библиотека предназначена для работы с десятичными числами, например, в бухгалтерии. У него по умолчанию нет функции для возврата числа десятичных знаков. Это особенно проблема, когда вы понимаете, что контекст, который он запускает, устанавливает его на то, что хочет пользователь.

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

Ваш лучший выбор, вероятно, будет падать на точку в вашей строке и подсчитывать количество символов в полученной подстроке.

Ответ 5

Если вы знаете, что у вас не будут проблемы с анализом (или если вы позволяете самому питону или какой-либо другой библиотеке обрабатывать это для вас, надеемся, что вы будете обрабатывать проблемы с локализацией)... просто проанализируйте его и используйте modf. Возвращаемое значение представляет собой пару значений, одна из которых является неотъемлемой частью, другая - дробной частью.

Ответ 6

Так как числа с плавающей запятой Python внутренне представлены как двоичные, а не десятичные, на самом деле нет ярлыка, кроме преобразования в десятичное. Единственный встроенный способ сделать это - преобразовать в строку. Вы можете написать свой собственный код, чтобы сделать десятичное преобразование и подсчитать цифры, но это будет дублирование усилий.

Ответ 7

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

str(number)[::-1].find('.')

Из-за проблемы с плавающей запятой все модули-модули дали мне ложные результаты даже с Decimal (number) (обратите внимание, что мне это нужно в script, чтобы исправить цены всего db)

len(str(Decimal(str(number))) % Decimal(1))) - 2

Необходимость поместить строку в Decimal довольно непростая, когда у нас есть плавающие или что-то вроде.

Вот моя "скамейка": https://repl.it/FM8m/17

Ответ 8

Самый быстрый способ, который я нашел для вычисления цифр после десятичной точки и округления числа, -

Вычислить цифры:

a=decimal.Decimal('56.9554362669143476');
lenstr = len(str(a).split(".")[1])

Калькуляция, проверка и округление:

a=decimal.Decimal('56.9554362669143476');
a = round(float(a),5) if len(str(a).split(".")[1]) > 5 else float(a)

Сравнение:

$ python2 -mtimeit 'import decimal; a=decimal.Decimal('56.9554362669143476'); round(float(a),5) if a.as_tuple().exponent < -5 else float(a)'
10000 loops, best of 3: 32.4 usec per loop
$ python -mtimeit 'import decimal; a=decimal.Decimal('56.9554362669143476'); a = round(float(a),5) if len(str(a).split(".")[1]) > 5 else float(a)'
100000 loops, best of 3: 16.7 usec per loop