使用json.loads时出现KeyError
JSON在处理以下语句时似乎出现了一些问题:
{"delete":{"status":{"id":12600579001,"user_id":55389449}}}
代码片段:
temp = json.loads(line)
text = temp['text']
当上面的代码片段遇到类似于上面这个JSON“字典”的行时,我得到了以下错误信息:
text = temp['text']
KeyError: 'text'
这是因为那一行没有“text”这个键,还是因为“delete”不在字典里呢?
10 个回答
是因为这一行里没有“text”这个键,还是因为“delete”不在字典里呢?
其实是因为没有“text”这个键。如果你用 print temp
打印一下,或者检查一下结果中的 Python 字典里有没有 'text'
这个键,你会发现根本没有叫 'text'
的键。实际上,temp
里只有一个键:'delete'
。而 'delete'
这个键对应的字典里只有一个键 'status'
,它又包含了一个字典,这个字典里有两个键:'user_id'
和 'id'
。
换句话说,你的结构是这样的:
{
"delete" : {
"status" : {
"id" : 12600579001,
"user_id" : 55389449
}
}
}
正如你所看到的,哪里都没有“text”这个键。
而且,你可以自己检查一下:
>>> 'text' in temp
False
>>> 'delete' in temp
True
如果你想在字典中查找一个键,但这个键可能不存在,可以使用 dict.get(key[, default]) 方法。比如说,使用 temp.get('text')
代替 temp['text']
。这样做的好处是,如果这个键不存在,程序不会报错,而是会返回一个空值 None
。
在Python中,有一种编程风格叫做EAFP(先请求原谅,再请求许可),这种方式比LBYL(先看再跳)更符合Python的风格。
看起来这个问题是因为里面没有'text'这个东西。也许你可以用下面的方式
'text' in temp
在尝试使用'text'之前,先检查一下它是否存在。
编辑:
我参考了评论中的例子,并在里面加了一个if/elif/else的结构。
#! /usr/bin/python
import sys
import json
f = open(sys.argv[1])
for line in f:
j = json.loads(line)
try:
if 'text' in j:
print 'TEXT: ', j['text']
elif 'delete' in j:
print 'DELETE: ', j['delete']
else:
print 'Everything: ', j
except:
print "EXCEPTION: ", j
示例片段 #1:
{u'favorited': False, u'contributors': None, u'truncated': False, u'text': ---- 省略 ---- }
示例片段 #2:
{u'delete': {u'status': {u'user_id': 55389449, u'id': 12600579001L}}}