在嵌套字典上使用ast.literal_eval

时间:2012-06-07 02:30:24

标签: python json dictionary eval abstract-syntax-tree

我使用ast.literal_eval将我从json.loads()收到的数据更改为Python字典;然而,如果我只是以一种完全不同的方式来解决这个问题 - 请随意指出这一点。

# Authentication
buf = StringIO.StringIO()
c = pycurl.Curl()
c.setopt(c.URL, "https://kippt.com/api/account")
c.setopt(c.WRITEFUNCTION, buf.write)
c.setopt(c.HTTPHEADER, header)
c.perform()

result = buf.getvalue()
buf.close()

print result

# Printing Output
data_string = json.dumps(result)
jsonload = json.loads(data_string)
jsondict = ast.literal_eval(jsonload)

目前它可以正常使用一行JSON返回,例如:

{"用户名":" my_username"," api_token":" my_api_token"}

我可以通过以下方式正确获取值:

print jsondict['username']
print jsondict['api_token']

我遇到问题的部分是嵌套数据的时间,例如:

  

{" meta":{" next":null," total_count":6," previous":null,&#34 ;极限&#34 ;:   20,"偏移":0},"对象":[{" rss_url":   " HTTPS://kippt.com/feed/username_here/stuff_here/cool-stuff" ;,   "更新":" 1339003710","标题":"酷东西","创建":   " 1339001514"," slug":" cool-stuff"," id":54533," resource_uri":   " / api / lists / 54533 /"},{" rss_url":   " HTTPS://kippt.com/feed/username_here/stuff_here/programming" ;,   "更新":" 1339003479","标题":"编程","创建":   " 1339001487"," slug":"编程"," id":54532," resource_uri":   " / api / lists / 54532 /"},{" rss_url":   " HTTPS://kippt.com/feed/username_here/stuff_here/android" ;,   "更新":" 1339003520","标题":" Android","创建":" 1339000936& #34 ;,   " slug":" android"," id":54530," resource_uri":" / api / lists / 54530 /& #34;},   {" rss_url&#34 ;:   " HTTPS://kippt.com/feed/username_here/stuff_here/chrome" ;,   "更新":" 1339000931","标题":" Chrome","创建":" 1339000412& #34 ;,   " slug":" chrome"," id":54529," resource_uri":" / api / lists / 54529 /& #34;},   {" rss_url&#34 ;:   " HTTPS://kippt.com/feed/username_here/stuff_here/inbox" ;,   "更新":" 1338946730","标题":"收件箱","创建":" 1338945940& #34 ;,   " slug":" inbox"," id":54432," resource_uri":" / api / lists / 54432 /& #34;},   {" rss_url&#34 ;:   " HTTPS://kippt.com/feed/username_here/stuff_here/read-later" ;,   "更新":" 1338945940","标题":"稍后阅读","创建":   " 1338945940"," slug":" read-later"," id":54433," resource_uri":   " / API /列表/ 54433 /"}]}

当我使用相同的代码(/ api / lists的Exchange URL)时,运行脚本时出现以下错误:

  

回溯(最近一次呼叫最后一次):文件" kippt.py",第48行,在          jsondict = ast.literal_eval(jsonload)File" /usr/local/lib/python2.7/ast.py" ;,第80行,在literal_eval中       返回_convert(node_or_string)文件" /usr/local/lib/python2.7/ast.py",第63行,在_convert中       在zip(node.keys,node.values))文件" /usr/local/lib/python2.7/ast.py",第62行,在       在_convert中为k,v文件" /usr/local/lib/python2.7/ast.py" ;,第63行返回dict((_ convert(k),_ convert(v))       在zip(node.keys,node.values))文件" /usr/local/lib/python2.7/ast.py",第62行,在       在_convert中为k,v文件" /usr/local/lib/python2.7/ast.py" ;,第79行返回dict((_ convert(k),_ convert(v))       引发ValueError('格式错误的字符串')ValueError:格式错误的字符串

任何帮助将不胜感激。谢谢!

编辑 - 答案如下:

看起来我的第一个输入可能被解释为Python语法,这就是我的错误所在,因为我在技术上并没有以正确的方式开始使用它。

我现在只想从cURL获取json.loads()我的结果,而不是做我以前做过的搞砸事情。

例如:

buf = StringIO.StringIO()
c = pycurl.Curl()
c.setopt(c.URL, "https://kippt.com/api/lists")
c.setopt(c.WRITEFUNCTION, buf.write)
c.setopt(c.HTTPHEADER, header)
c.perform()

result = buf.getvalue()
buf.close()

print result

# Printing Output
jsonload = json.loads(result)
print jsonload['meta']['total_count'] # Gets the total_count item in the meta object.

2 个答案:

答案 0 :(得分:6)

ast.literal_eval嵌套词典没有问题:

>>> ast.literal_eval("{'a': {'b':'c'}}")
{'a': {'b': 'c'}}

ast.literal_eval正在破碎,因为数据实际上是JSON ......而且JSON不是有效的Python。具体来说,null不是有效的Python文字。

为什么不使用json.loads()加载数据?

答案 1 :(得分:0)

我想到了一种情况,在这种情况下,我想在熊猫中使用json.normalize,但是值是str类型的。使用ast.literal_eval,我输入强制转换

您可以像下面那样使用ast.literal_eval- df [column_name] = df [column_name] .apply(ast.literal_eval)

这会将str转换为dict。 例如 df = [{'A':“ {'value':'1'}”,'B':“ {'value':'2'}”}]

应用文字评估后- df = [{'A':{'value':'1'},'B':{'value':'2'}}]