PYTHON: 是否有类似于 ast.literal_eval() 的函数?

3
我在使用ast.literal_eval()时遇到了问题。在下面的示例中,我只想将字符串(myText)转换为字典。但是ast.literal_eval()尝试评估<__main__.myClass instance at 0x0000000052D64D88>并给出错误。我完全理解这个错误,但我想知道是否有一种方法可以避免它(使用其他函数或以其他方式使用ast.literal_eval函数)。
import ast

myText = "{<__main__.myClass instance at 0x0000000052D64D88>: value}"
ast.literal_eval(myText)

# Error: invalid syntax
# Traceback (most recent call last):
#   File "<maya console>", line 4, in <module>
#   File "C:\Program Files\Autodesk\Maya2016\bin\python27.zip\ast.py", line 49, in literal_eval
#     node_or_string = parse(node_or_string, mode='eval')
#   File "C:\Program Files\Autodesk\Maya2016\bin\python27.zip\ast.py", line 37, in parse
#     return compile(source, filename, mode, PyCF_ONLY_AST)
#   File "<unknown>", line 1
#     {<__main__.myClass instance at 0x0000000052D64D88>: value}
#      ^
# SyntaxError: invalid syntax # 

感谢您的帮助!

以下是关于IT技术的翻译内容:


如果你知道 myText 是比较规则的,考虑手动处理。具体步骤如下:1. 去掉大括号。2. 按逗号分割。3. 将每个结果字符串按冒号分割,并将各部分存入字典中。 - unwind
3
在这里,你希望发生什么? - Daniel Roseman
4
如果你将这种信息存储为字符串,那么你可能正在错误地尝试解决问题。你试图解决什么根本问题/想要评估这个字符串的作用是什么? - syntonym
1
您的数据已经不可逆地损坏了。使用更智能的解析器也无济于事。 - Ignacio Vazquez-Abrams
我可以像unwind说的那样手动尝试执行它。实际上,我尝试读取一个文本文件。在这个文件中,我保存了几个实例的属性,现在我想要获取这些值。所以实际上我想要读取的字符串更像是这样的: {<__main__.myClass instance at 0x0000000052D64D88>: {'name': 'theName'}, <__main__.myClass instance at 0x0000000052D73F48>: {'name': 'theName'}} - Morgan
显示剩余4条评论
1个回答

3
你真正想做的是使用pickle.dump转储数据,使用pickle.load(或等效物,例如json等)加载它。使用repr(data)来转储数据会导致像这样的问题。
如果您只需要挽救已经生成的数据,您可能可以尝试以下操作:
def my_literal_eval(s):
    s = re.sub(r"<__main__.myClass instance at 0x([^>]+)>", r'"<\1>"', s)
    dct = ast.literal_eval(s)
    return {myClass(): v for v in dct.itervalues()}

使用示例:

>>> import ast, re
>>> class myClass(object): pass
... 
>>> myText = "{<__main__.myClass instance at 0x0000000052D64D88>: {'name': 'theName'}, <__main__.myClass instance at 0x0000000052D73F48>: {'name': 'theName'}}"
>>> my_literal_eval(myText)
{<__main__.myClass object at 0x7fbdc00a4b90>: {'name': 'theName'}, <__main__.myClass object at 0x7fbdc0035550>: {'name': 'theName'}}

这只有在 myClass 实例没有任何有用信息而仅需要用于标识时才有效。其想法是首先通过替换 <__main__.myClass instance ...> 字符串来修复字符串,以便可以通过 ast.literal_eval 进行解析,然后用实际的 myClass 实例替换它们 - 前提是这些实例可以在不需要参数的情况下构造,这取决于上述假设。
如果这个最初的假设不成立,则你的数据就像 Ignacio 所说 的那样,已经无法挽回地损坏了,任何聪明的解析也无法检索丢失的位。

谢谢!看起来完美符合我的要求! - Morgan

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接