Lưu ý rằng các trick ceil(num * 100)/100
sẽ sụp đổ trên một số đầu vào thoái hóa, như 1e308. Điều này có thể không xuất hiện thường xuyên nhưng tôi có thể nói với bạn rằng nó chỉ chi phí cho tôi một vài ngày. Để tránh điều này, "sẽ rất tuyệt nếu" ceil()
và floor()
lấy một đối số vị trí thập phân, như round()
hiện ... Trong khi đó, bất kỳ ai biết một giải pháp thay thế sạch sẽ sẽ không gặp sự cố về đầu vào như thế này? Tôi đã có một số hy vọng về gói decimal
nhưng có vẻ như chết quá:
>>> from math import ceil
>>> from decimal import Decimal, ROUND_DOWN, ROUND_UP
>>> num = 0.1111111111000
>>> ceil(num * 100)/100
0.12
>>> float(Decimal(num).quantize(Decimal('.01'), rounding=ROUND_UP))
0.12
>>> num = 1e308
>>> ceil(num * 100)/100
Traceback (most recent call last):
File "<string>", line 301, in runcode
File "<interactive input>", line 1, in <module>
OverflowError: cannot convert float infinity to integer
>>> float(Decimal(num).quantize(Decimal('.01'), rounding=ROUND_UP))
Traceback (most recent call last):
File "<string>", line 301, in runcode
File "<interactive input>", line 1, in <module>
decimal.InvalidOperation: [<class 'decimal.InvalidOperation'>]
Tất nhiên người ta có thể nói bị rơi đó là hành vi lành mạnh chỉ trên đầu vào như vậy, nhưng tôi cho rằng nó không phải là làm tròn nhưng nhân đó là nguyên nhân gây ra vấn đề (đó là lý do tại sao, ví dụ, 1e306 không sụp đổ), và việc thực hiện sạch hơn của fn round-up-nnth-place sẽ tránh được việc hack nhân.
Nguồn
2015-02-02 06:26:01
Tôi khuyên bạn nên đọc [Số học dấu chấm động: Các vấn đề và giới hạn] (http://docs.python.org/tutorial/floatingpoint.html) từ hướng dẫn Python trước khi bạn tiếp tục. –
Ngoài ra, hãy cân nhắc xem bạn có thực sự muốn làm tròn các giá trị hay bạn chỉ muốn * hiển thị * chúng với 3 chữ số thập phân ... – geoffspear