python2.7 读取字符串,unicode编码转中文

问题描述

读取一个字符串test_str,字符串是一个嵌套的json串,且含有list类型数据,其中含有中文。我需要抽取其中的某些字段,存于一个新的文件。

>>>test_str='{"username":"tom","hobby":["足球","篮球","乒乓球"]}'

最开始使用json.loads(test_str)

>>>import json
>>>json.loads(test_str)
>>>{u'username': u'tom', u'hobby': [u'\u8db3\u7403', u'\u7bee\u7403', u'\u4e52\u4e53\u7403']}

得到结果,数据前面都加上了 u,中文也变成了'\u8db3\u7403'之类的。
很明显又碰到了python2中文编码的坑,于是网上搜索解决办法。
试了一些方法,都无效或者报错:

'ascii' codec can't encode character u'\u2019'

尝试过的无效解决方法1

在代码开头加:
import sys
reload(sys)
sys.setdefaultencoding('utf-8')

尝试过的无效解决方法2

['hobby'][0].decode('unicode-escape')
或者
['hobby'][0].decode('utf-8')
等等一些encode('gbk')之类的

尝试过的无效解决方法3

在代码开头加:
# -- coding: utf-8 --

解决方案

后来搜索发现,josn.loads会默认将数据load成Unicode对象
转换搜索方向,从这里发现两个可行方法:

解决方法1

使用PyYaml包,但是只能将最外层的数据编码格式转换正确,里层的还是unicode编码:
>>>aml.safe_load(test_str)
{'username': 'tom', 'hobby': [u'\u8db3\u7403', u'\u7bee\u7403', u'\u4e52\u4e53\u7403']}

解决方法2

使用如下代码彻底解决,,数据存储到文件里还是乱码,但是读出来可以中文显示:
>>>data = json_loads_byteified(r)
>>>data
{'username': 'tom', 'hobby': ['\xe8\xb6\xb3\xe7\x90\x83', '\xe7\xaf\xae\xe7\x90\x83', '\xe4\xb9\x92\xe4\xb9\x93\xe7\x90\x83']}
>>>print data['hobby'][0]
足球

import json

def json_load_byteified(file_handle):
    return _byteify(
        json.load(file_handle, object_hook=_byteify),
        ignore_dicts=True
    )

def json_loads_byteified(json_text):
    return _byteify(
        json.loads(json_text, object_hook=_byteify),
        ignore_dicts=True
    )

def _byteify(data, ignore_dicts = False):
    # if this is a unicode string, return its string representation
    if isinstance(data, unicode):
        return data.encode('utf-8')
    # if this is a list of values, return list of byteified values
    if isinstance(data, list):
        return [ _byteify(item, ignore_dicts=True) for item in data ]
    # if this is a dictionary, return dictionary of byteified keys and values
    # but only if we haven't already byteified it
    if isinstance(data, dict) and not ignore_dicts:
        return {
            _byteify(key, ignore_dicts=True): _byteify(value, ignore_dicts=True)
            for key, value in data.iteritems()
        }
    # if it's anything else, return it in its original form
    return data

你可能感兴趣的:(python2.7 读取字符串,unicode编码转中文)