Как лучше округлить поплавок в эликсире?

Я пытаюсь округлить Float в эликсире до 2 знаков после запятой.

Если у меня есть число 12.555, я бы хотел, чтобы моя функция округления возвращала 12.56

Первоначально я думал, что Float.round — это то, что мне нужно, но эта функция не всегда возвращает значение. ответ, который я хотел бы.

Например...

iex()> Float.round(12.555, 2)
12.55

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

Мое текущее решение...

iex()> round(12.555 * 100) / 100
12.56

Это делает работу, но, как я уже сказал, я просто хотел знать, есть ли лучшее решение.

заранее спасибо


person RobStallion    schedule 08.04.2019    source источник
comment
Это не имеет ничего общего с Elixir, но с числами с плавающей запятой IEEE 754; см. также hexdocs.pm/elixir/Float.html#round/2   -  person coproc    schedule 08.04.2019
comment
@coproc, пожалуйста, не стесняйтесь обновлять флаги, если вы считаете, что они не точны.   -  person RobStallion    schedule 09.04.2019


Ответы (2)


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

12.555
|> Decimal.from_float()
|> Decimal.round(2)

Выход:

#Decimal<12.56>

Затем вы можете использовать такие функции, как Decimal.to_string/2 для печати или Decimal.to_float/1, но имейте в виду, что to_float/1 также является неточной операцией и может привести к сбою.

person Adam Millerchip    schedule 08.04.2019

Float.ceil/2 может помочь вам в этом, если вы не хотите использовать библиотеку

iex> 12.555 |> Float.ceil(2)        
12.56
person BlueGene    schedule 12.09.2019
comment
Нет, если вам нужно разумное десятичное поведение. Например, Float.ceil(0.2, 1) и Float.ceil(0.3, 1) производят 0.3. floating-point-gui.de - person Adam Millerchip; 11.06.2020