Python如何eval一个精度为十进制的列表字符串?

时间:2017-02-20 15:41:22

标签: python python-2.7 floating-point decimal

我有一个像这样的列表

的字符串
list_str = '[148654.08425925925, 148656.99994212962, 148658.08229166668, 148661.0020601852]'

然后我使用eval()将它转换为Python中的真实列表对象

print eval(list_str)

然而,输出是四舍五入的,我不想

0 = {float} 148654.084259
1 = {float} 148656.999942
2 = {float} 148658.082292
3 = {float} 148661.00206

我怎样才能使值保持为String(精确到十进制)?

我需要使用eval(),因为它也会在此列表中使用其他操作

3 个答案:

答案 0 :(得分:1)

虽然浮点可能会丢失精度,但这里没有精度损失,因为看起来字符串是从Python的浮点列表开始生成的。请注意,建议ast.literal_eval优先于eval,但是:

>>> list_str = '[148654.08425925925, 148656.99994212962, 148658.08229166668, 148661.0020601852]'
>>> import ast
>>> L = ast.literal_eval(list_str)
>>> L
[148654.08425925925, 148656.99994212962, 148658.08229166668, 148661.0020601852]

请注意,上面与原始字符串完全匹配。但是,打印单个浮动而不是整个列表默认为小数点后的六位数,因此如果您想要更高的精度,请指定它:

>>> for f in L:
...     print '{:.11f}'.format(f)
...     
148654.08425925925
148656.99994212962
148658.08229166668
148661.00206018519

我还建议您首先查看picklejson模块以保存列表,以避免使用eval甚至ast.literal_eval

答案 1 :(得分:0)

在python中使用Decimal

from decimal import *
mlist = '[148654.08425925925, 148656.99994212962, 148658.08229166668, 148661.0020601852]'
mlisttrim = mlist[1:-1]
l = []
for i in mlisttrim.split(', '):
    l.append(Decimal(i))
print l

答案 2 :(得分:0)

floats由二进制分数表示,当您使用的点分十进制表示(see here)进行转换时,精度会下降。 python decimal package实现了十进制浮点运算,并没有这个限制。

您不能使用eval来分解列表,因为这些值将评估为浮点数,但您可以使用正则表达式包来提取浮点数并从那里构建列表。

>>> import decimal
>>> import re
>>> list_str = '[148654.08425925925, 148656.99994212962, 148658.08229166668, 148661.0020601852]'
>>> items = [decimal.Decimal(x) for x in re.findall(r'\d+\.?\d*', list_str)]
>>> items
[Decimal('148654.08425925925'), Decimal('148656.99994212962'), Decimal('148658.08229166668'), Decimal('148661.0020601852')]
>>>