解析JSON格式Twitter数据时出现额外None值的问题排查
我来帮你排查这个问题,你的代码逻辑方向是对的,但有几个细节没处理好,导致输出里出现了额外的None值,咱们一步步分析:
问题原因
异常未捕获导致的返回None:
有些JSON虽然有created_at字段,但可能缺少user字段,或者user对象里没有id_str,这时候调用tmp.get('user').get('id_str')会触发AttributeError(因为tmp.get('user')返回None后,再调用.get()方法就会报错),而你的代码没有捕获这个异常,导致get_usr_txt函数异常退出,最终返回None。不完整推文未被过滤:
你的safe_parse只检查了created_at字段,但有些包含created_at的消息可能不是完整的推文(比如缺失user或text),这类消息会被safe_parse返回,但后续处理时因为字段缺失,要么报错返回None,要么返回包含None的元组,最终出现在输出里。函数返回值不明确:
你的代码里return(没有写None)虽然在Python中等同于返回None,但这种写法容易混淆,也不利于排查问题。
解决方法
我们可以从三个层面修复代码:过滤无效消息、避免异常、过滤最终结果。
1. 修复safe_parse函数
提前过滤掉没有created_at和user字段的消息,同时明确返回None:
import json def safe_parse(raw_json): try: json_object = json.loads(raw_json) # 只保留同时包含created_at和user的有效推文 if 'created_at' in json_object and 'user' in json_object: return json_object else: return None except ValueError as error: return None
2. 修复get_usr_txt函数
增加对id_str和text字段的检查,避免异常,同时确保只有有效数据才返回:
def get_usr_txt(line): tmp = safe_parse(line.strip()) # 记得去掉换行符,避免解析失败 if tmp is not None: # 分别获取字段,避免链式调用的异常 user_id = tmp['user'].get('id_str') tweet_text = tmp.get('text') # 确保两个字段都有效才返回元组 if user_id and tweet_text: return (user_id, tweet_text) # 任何不符合条件的情况都返回None return None
3. 处理结果时过滤None
在读取文件处理每一行的时候,只保留非None的结果:
with open('your_twitter_stream.txt', 'r') as stream_file: valid_tweets = [] for line in stream_file: tweet_data = get_usr_txt(line) if tweet_data is not None: valid_tweets.append(tweet_data) # 现在valid_tweets里只有有效的用户ID和文本元组 print(valid_tweets)
为什么这样有效?
- 你提到的limit通知(比如
{"limit":{"track":1,"timestamp_ms":"1456249416070"}})因为没有created_at字段,会被safe_parse直接过滤,返回None,最终不会进入结果列表。 - 对于有
created_at但缺失user、id_str或text的不完整消息,要么被safe_parse过滤,要么被get_usr_txt返回None,最后被过滤掉。 - 明确的返回值和字段检查,避免了异常导致的意外None。
内容的提问来源于stack exchange,提问作者Rvsvgs
相关产品推荐
相关产品推荐

