Tar*_*rGz 161 python floating-point formatting pretty-print
如何格式化浮点数,使其不包含剩余的零?换句话说,我希望得到的字符串尽可能短..?
喜欢:
3 -> "3"
3. -> "3"
3.0 -> "3"
3.1 -> "3.1"
3.14 -> "3.14"
3.140 -> "3.14"
Run Code Online (Sandbox Code Playgroud)
Ale*_*lli 166
我,我会做('%f' % x).rstrip('0').rstrip('.')- 保证定点格式而不是科学记谱法等等.是的,不像光滑和优雅%g,但是,它有效(我不知道如何强迫%g永远不要使用科学记数法; - ).
unu*_*tbu 133
你可以%g用来实现这个目标:
'%g'%(3.140)
Run Code Online (Sandbox Code Playgroud)
或者,对于Python 2.6或更高版本:
'{0:g}'.format(3.140)
Run Code Online (Sandbox Code Playgroud)
来自以下文档format:g原因(除其他外)
从有效数字中删除无关紧要的尾随零,如果后面没有剩余数字,也会删除小数点.
And*_*der 12
尝试最简单,最有效的方法怎么样?normalize()方法删除所有最右边的尾随零.
from decimal import Decimal
print (Decimal('0.001000').normalize())
# Result: 0.001
Run Code Online (Sandbox Code Playgroud)
适用于Python 2和Python 3.
- 更新 -
@ BobStein-VisiBone指出的唯一问题是,10,100,1000等数字将以指数表示形式显示.这可以使用以下函数轻松修复:
from decimal import Decimal
def format_float(f):
d = Decimal(str(f));
return d.quantize(Decimal(1)) if d == d.to_integral() else d.normalize()
Run Code Online (Sandbox Code Playgroud)
Pol*_*esh 10
在查看几个类似问题的答案之后,这对我来说似乎是最好的解决方案:
def floatToString(inputValue):
return ('%.15f' % inputValue).rstrip('0').rstrip('.')
Run Code Online (Sandbox Code Playgroud)
我的推理:
%g 没有摆脱科学记数法.
>>> '%g' % 0.000035
'3.5e-05'
Run Code Online (Sandbox Code Playgroud)
15个小数位似乎可以避免奇怪的行为,并且对我的需求有很大的精确度.
>>> ('%.15f' % 1.35).rstrip('0').rstrip('.')
'1.35'
>>> ('%.16f' % 1.35).rstrip('0').rstrip('.')
'1.3500000000000001'
Run Code Online (Sandbox Code Playgroud)
我可以使用format(inputValue, '.15f').而不是'%.15f' % inputValue,但这有点慢(~30%).
我本可以使用Decimal(inputValue).normalize(),但这也有一些问题.首先,它慢了很多(~11x).我还发现虽然它具有非常高的精度,但在使用时仍然会遭受精确损失normalize().
>>> Decimal('0.21000000000000000000000000006').normalize()
Decimal('0.2100000000000000000000000001')
>>> Decimal('0.21000000000000000000000000006')
Decimal('0.21000000000000000000000000006')
Run Code Online (Sandbox Code Playgroud)
最重要的是,我仍然会转而Decimal使用float能够让你最终得到的东西,而不是你放在那里的数字.Decimal当算术保持在Decimal并且Decimal用字符串初始化时,我认为效果最好.
>>> Decimal(1.35)
Decimal('1.350000000000000088817841970012523233890533447265625')
>>> Decimal('1.35')
Decimal('1.35')
Run Code Online (Sandbox Code Playgroud)
我确定Decimal.normalize()可以使用上下文设置调整精度问题,但考虑到已经很慢的速度并且不需要荒谬的精度,而且我仍然会从浮动转换并且无论如何都会失去精度,我没有我认为值得追求.
我不关心可能的"-0"结果,因为-0.0是一个有效的浮点数,无论如何它可能是罕见的,但是既然你提到你想要保持字符串结果尽可能短,你总是可以在非常小的额外速度成本下使用额外的条件.
def floatToString(inputValue):
result = ('%.15f' % inputValue).rstrip('0').rstrip('.')
return '0' if result == '-0' else result
Run Code Online (Sandbox Code Playgroud)
这是一个对我有用的解决方案。这是一个混合的解决方案通过多网并使用新的.format() 语法。
for num in 3, 3., 3.0, 3.1, 3.14, 3.140:
print('{0:.2f}'.format(num).rstrip('0').rstrip('.'))
Run Code Online (Sandbox Code Playgroud)
输出:
3
3
3
3.1
3.14
3.14
Run Code Online (Sandbox Code Playgroud)
如果您想要同时适用于数字或字符串输入的东西(感谢@mike-placentra 寻找错误):
def num(s):
""" 3.0 -> 3, 3.001000 -> 3.001 otherwise return s """
s = str(s)
try:
int(float(s))
if '.' not in s:
s += '.0'
return s.rstrip('0').rstrip('.')
except ValueError:
return s
>>> for n in [3, 3., 3.0, 3.1, 3.14, 3.140, 3.001000, 30 ]: print(num(n))
...
3
3
3
3.1
3.14
3.14
3.001
30
>>> for n in [3, 3., 3.0, 3.1, 3.14, 3.140, 3.001000, 30 ]: print(num(str(n)))
...
3
3
3
3.1
3.14
3.14
3.001
30
Run Code Online (Sandbox Code Playgroud)
您可以简单地使用 format() 来实现这一点:
format(3.140, '.10g')其中 10 是您想要的精度。
| 归档时间: |
|
| 查看次数: |
98373 次 |
| 最近记录: |