`
lantian_123
  • 浏览: 1368503 次
  • 性别: Icon_minigender_1
  • 来自: 广州
社区版块
存档分类
最新评论

Python处理JSON

 
阅读更多

Python处理JSON


(如果阅读效果不佳,可戳这里

概念

序列化(Serialization):将对象的状态信息转换为可以存储或可以通过网络传输的过程,传输的格式可以是JSON、XML等。反序列化就是从存储区域(JSON,XML)读取反序列化对象的状态,重新创建该对象。

JSON(JavaScript Object Notation):一种轻量级数据交换格式,相对于XML而言更简单,也易于阅读和编写,机器也方便解析和生成,Json是JavaScript中的一个子集。

Python2.6开始加入了JSON模块,无需另外下载,Python的Json模块序列化与反序列化的过程分别是 encoding和 decoding

encoding:把一个Python对象编码转换成Json字符串
decoding:把Json格式字符串解码转换成Python对象
对于简单数据类型(string、unicode、int、float、list、tuple、dict),可以直接处理。

json.dumps方法对简单数据类型encoding:
import json
data = [{'a':"A",'b':(2,4),'c':3.0}]  #list对象
print "DATA:",repr(data)

data_string = json.dumps(data)
print "JSON:",data_string

输出:

DATA: [{'a':'A','c':3.0,'b':(2,4)}] #python的dict类型的数据是没有顺序存储的
JSON: [{"a":"A","c":3.0,"b":[2,4]}]  

JSON的输出结果与DATA很相似,除了一些微妙的变化,如python的元组类型变成了Json的数组,Python到Json的编码转换规则是: python2json

json.loads方法处理简单数据类型的decoding(解码)转换
import json
data = [{'a':"A",'b':(2,4),'c':3.0}]  #list对象

data_string = json.dumps(data)
print "ENCODED:",data_string

decoded = json.loads(data_string)
print "DECODED:",decoded

print "ORIGINAL:",type(data[0]['b'])
print "DECODED:",type(decoded[0]['b'])

输出:

ENCODED: [{"a": "A", "c": 3.0, "b": [2, 4]}]
DECODED: [{u'a': u'A', u'c': 3.0, u'b': [2, 4]}]
ORIGINAL: <type 'tuple'>
DECODED: <type 'list'>

解码过程中,json的数组最终转换成了python的list,而不是最初的tuple类型,Json到Python的解码规则是: json2python

json的人文关怀

编码后的json格式字符串紧凑的输出,而且也没有顺序,因此dumps方法提供了一些可选的参数,让输出的格式提高可读性,如sort_keys是告诉编码器按照字典排序(a到z)输出。

import json

data = [ { 'a':'A', 'b':(2, 4), 'c':3.0 } ]
print 'DATA:', repr(data)

unsorted = json.dumps(data)
print 'JSON:', json.dumps(data)
print 'SORT:', json.dumps(data, sort_keys=True)

输出:

DATA: [{'a': 'A', 'c': 3.0, 'b': (2, 4)}]
JSON: [{"a": "A", "c": 3.0, "b": [2, 4]}]
SORT: [{"a": "A", "b": [2, 4], "c": 3.0}

indent参数根据数据格式缩进显示,读起来更加清晰:

import json

data = [ { 'a':'A', 'b':(2, 4), 'c':3.0 } ]
print 'DATA:', repr(data)

print 'NORMAL:', json.dumps(data, sort_keys=True)
print 'INDENT:', json.dumps(data, sort_keys=True, indent=2)

输出:

DATA: [{'a': 'A', 'c': 3.0, 'b': (2, 4)}]
NORMAL: [{"a": "A", "b": [2, 4], "c": 3.0}]
INDENT: [
  {
    "a": "A",
    "b": [
      2,
      4
    ],
    "c": 3.0
  }
]

separators参数的作用是去掉,,:后面的空格,从上面的输出结果都能看到", :"后面都有个空格,这都是为了美化输出结果的作用,但是在我们传输数据的过程中,越精简越好,冗余的东西全部去掉,因此就可以加上separators参数:

import json

data = [ { 'a':'A', 'b':(2, 4), 'c':3.0 } ]
print 'DATA:', repr(data)
print 'repr(data)             :', len(repr(data))
print 'dumps(data)            :', len(json.dumps(data))
print 'dumps(data, indent=2)  :', len(json.dumps(data, indent=2))
print 'dumps(data, separators):', len(json.dumps(data, separators=(',',':')))

输出:

DATA: [{'a': 'A', 'c': 3.0, 'b': (2, 4)}]
repr(data)             : 35
dumps(data)            : 35
dumps(data, indent=2)  : 76
dumps(data, separators): 29

skipkeys参数,在encoding过程中,dict对象的key只可以是string对象,如果是其他类型,那么在编码过程中就会抛出ValueError的异常。skipkeys可以跳过那些非string对象当作key的处理.

import json

data= [ { 'a':'A', 'b':(2, 4), 'c':3.0, ('d',):'D tuple' } ]

try:
    print json.dumps(data)
except (TypeError, ValueError) as err:
    print 'ERROR:', err
print 
print json.dumps(data, skipkeys=True)

输出:

ERROR: keys must be a string

[{"a": "A", "c": 3.0, "b": [2, 4]}]

让json支持自定义数据类型

以上例子都是基于python的built-in类型的,对于自定义类型的数据结构,json模块默认是没法处理的,会抛出异常:TypeError xx is not JSON serializable,此时你需要自定义一个转换函数:

import json  

class MyObj(object):
    def __init__(self, s):
        self.s = s
    def __repr__(self):
        return '<MyObj(%s)>' % self.s

obj = .MyObj('helloworld')

try:
    print json.dumps(obj)
except TypeError, err:
    print 'ERROR:', err

#转换函数
def convert_to_builtin_type(obj):
    print 'default(', repr(obj), ')'
    # 把MyObj对象转换成dict类型的对象
    d = { '__class__':obj.__class__.__name__, 
          '__module__':obj.__module__,
        }
    d.update(obj.__dict__)
    return d

print json.dumps(obj, default=convert_to_builtin_type)

输出:

ERROR: <MyObj(helloworld)> is not JSON serializable
default( <MyObj(helloworld)> )
{"s": "hellworld", "__module__": "MyObj", "__class__": "__main__"} 
#注意:这里的class和module根据你代码的所在文件位置不同而不同

相反,如果要把json decode 成python对象,同样也需要自定转换函数,传递给json.loads方法的object_hook参数:

#jsontest.py

import json

class MyObj(object):

    def __init__(self,s):
        self.s = s

    def __repr__(self):

        return "<MyObj(%s)>" % self.s

def dict_to_object(d):
    if '__class__' in d:
        class_name = d.pop('__class__')
        module_name = d.pop('__module__')
        module = __import__(module_name)

        print "MODULE:",module

        class_ = getattr(module,class_name)

        print "CLASS",class_

        args = dict((key.encode('ascii'),value) for key,value in d.items())

        print 'INSTANCE ARGS:',args

        inst = class_(**args)
    else:
        inst = d
    return inst

encoded_object = '[{"s":"helloworld","__module__":"jsontest","__class__":"MyObj"}]'

myobj_instance = json.loads(encoded_object,object_hook=dict_to_object)
print myobj_instance

输出:

MODULE: <module 'jsontest' from 'E:\Users\liuzhijun\workspace\python\jsontest.py'>
CLASS <class 'jsontest.MyObj'>
INSTANCE ARGS: {'s': u'helloworld'}
[<MyObj(helloworld)>]
MODULE: <module 'jsontest' from 'E:\Users\liuzhijun\workspace\python\jsontest.py'>
CLASS <class 'jsontest.MyObj'>
INSTANCE ARGS: {'s': u'helloworld'}
[<MyObj(helloworld)>]

使用Encoder与Decoder类实现json编码的转换

JSONEncoder有一个迭代接口iterencode(data),返回一系列编码的数据,他的好处是可以方便的把逐个数据写到文件或网络流中,而不需要一次性就把数据读入内存.

import json

encoder = json.JSONEncoder()
data = [ { 'a':'A', 'b':(2, 4), 'c':3.0 } ]

for part in encoder.iterencode(data):
    print 'PART:', part

输出:

PART: [
PART: {
PART: "a"
PART: :
PART: "A"
PART: ,
PART: "c"
PART: :
PART: 3.0
PART: ,
PART: "b"
PART: :
PART: [2
PART: , 4
PART: ]
PART: }
PART: ]

encode方法等价于''.join(encoder.iterencode(),而且预先会做些错误检查(比如非字符串作为dict的key),对于自定义的对象,我们只需从些JSONEncoder的default()方法,其实现方式与上面提及的函数convet_to_builtin_type()是类似的。

import json
import json_myobj

class MyObj(object):

    def __init__(self,s):
        self.s = s

    def __repr__(self):
        return "<MyObj(%s)>" % self.s

class MyEncoder(json.JSONEncoder):

    def default(self, obj):
        print 'default(', repr(obj), ')'
        # Convert objects to a dictionary of their representation
        d = { '__class__':obj.__class__.__name__, 
              '__module__':obj.__module__,
              }
        d.update(obj.__dict__)
        return d

obj = json_myobj.MyObj('helloworld')
print obj
print MyEncoder().encode(obj)

输出:

<MyObj(internal data)>
default( <MyObj(internal data)> )
{"s": "helloworld", "__module__": "Myobj", "__class__": "MyObj"}

从json对Python对象的转换:

class MyDecoder(json.JSONDecoder):

    def __init__(self):
        json.JSONDecoder.__init__(self, object_hook=self.dict_to_object)

    def dict_to_object(self, d):
        if '__class__' in d:
            class_name = d.pop('__class__')
            module_name = d.pop('__module__')
            module = __import__(module_name)
            print 'MODULE:', module
            class_ = getattr(module, class_name)
            print 'CLASS:', class_
            args = dict( (key.encode('ascii'), value) for key, value in d.items())
            print 'INSTANCE ARGS:', args
            inst = class_(**args)
        else:
            inst = d
        return inst

encoded_object = '[{"s": "helloworld", "__module__": "jsontest", "__class__": "MyObj"}]'

myobj_instance = MyDecoder().decode(encoded_object)
print myobj_instance

输出:

MODULE: <module 'jsontest' from 'E:\Users\liuzhijun\workspace\python\jsontest.py'>
CLASS: <class 'jsontest.MyObj'>
INSTANCE ARGS: {'s': u'helloworld'}
[<MyObj(helloworld)>]

json格式字符串写入到文件流中

上面的例子都是在内存中操作的,如果对于大数据,把他编码到一个类文件(file-like)中更合适,load()dump()方法就可以实现这样的功能。

import json
import tempfile

data = [ { 'a':'A', 'b':(2, 4), 'c':3.0 } ]

f = tempfile.NamedTemporaryFile(mode='w+')
json.dump(data, f)
f.flush()

print open(f.name, 'r').read()

输出:

[{"a": "A", "c": 3.0, "b": [2, 4]}]

类似的:

import json
import tempfile

f = tempfile.NamedTemporaryFile(mode='w+')
f.write('[{"a": "A", "c": 3.0, "b": [2, 4]}]')
f.flush()
f.seek(0)

print json.load(f)

输出:

[{u'a': u'A', u'c': 3.0, u'b': [2, 4]}]

参考:
http://docs.python.org/2/library/json.html
http://www.cnblogs.com/coser/archive/2011/12/14/2287739.html
http://pymotw.com/2/json/

 

1
2
分享到:
评论

相关推荐

    一个简单的示例演示如何使用 Python 处理 JSON 数据

    一个简单的示例演示如何使用 Python 处理 JSON 数据. 解析 JSON 数据; 将 Python 对象转换为 JSON 数据 在这个示例中,json.loads() 函数用于将 JSON 格式的字符串解析为 Python 字典,而 json.dumps() 函数用于将 ...

    python经典入门100例 + python操作json、xml、MySQL

    本资源包涵盖了Python的经典入门实例,以及如何使用Python处理JSON、XML数据和操作MySQL数据库,这些都是Python开发者必备的技能。 首先,Python经典入门100例是初学者学习Python语法和常用库的绝佳资源。这100个...

    python 处理json数据(csdn)————程序.pdf

    Python处理JSON数据是编程中常见的任务,特别是在Web开发和数据交换场景下。JSON(JavaScript Object Notation)是一种轻量级的数据交换格式,它易于人阅读和编写,同时也易于机器解析和生成。在Python中,我们可以...

    python解析json的代码

    这个文件可能包含了一个或多个Python脚本,以及相应的测试文件,用于演示如何使用Python处理JSON数据。 综上所述,这个主题涉及的核心知识点包括Python的`json`模块,`json.loads()`函数,JSON数据的解析,以及编写...

    Python处理JSON.doc

    Python从2.6版本开始内置了JSON模块,使得处理JSON数据变得非常便捷。 **序列化与反序列化** 1. **序列化(Serialization)**:序列化是将Python对象转换为JSON格式字符串的过程,以便于存储或在网络中传输。...

    python json文件转txt文件,批处理json文件转换成一个txt文件

    1. **导入必要的库**:首先,我们需要导入`json`库,它是Python处理JSON数据的核心库。 ```python import json ``` 2. **定义转换函数**:创建一个函数,接收JSON文件的路径作为参数,然后打开并读取文件,再使用`...

    Python 写入json文件内容换行显示(csdn)————程序.pdf

    在处理JSON数据时,有时我们需要将数据写入到JSON文件中,以便于存储或后续处理。当我们在Python中使用`json.dump()`函数向JSON文件写入内容时,如果不进行特殊设置,内容通常会以紧凑的形式(即一行内显示所有内容...

    json_with_python_symbian_60.rar_json symbian_python_python json_

    总的来说,这个压缩包提供的资源对于学习如何在Symbian 60系统上使用Python处理JSON数据非常有价值。它展示了从创建JSON对象,到通过网络发送和接收JSON数据的完整流程,这对于移动开发,特别是涉及数据交换的场景,...

    Python处理JSON数据并生成条形图

    ### Python处理JSON数据并生成条形图 #### 一、JSON数据准备与解析 在开始之前,我们需要准备一份JSON格式的数据。在这个例子中,我们假设有一份包含3560条记录的JSON文件,每条记录都具有多个字段,其中包括`tz`...

    浅谈python处理json和redis hash的坑

    在使用Python处理JSON数据以及与Redis的hash类型交互时,开发者往往会遇到一些常见的问题,这篇文章将深入探讨这些问题并提供相应的解决方案。首先,我们来看一下文章的标题和描述。 文章标题是“浅谈Python处理...

    使用 Python 处理 JSON 格式的数据

    下面就来介绍一下如何使用 Python 处理 JSON 数据。 JSON 的全称是 JavaScript 对象表示法 JavaScript Object Notation 。这是一种以键值对的形式存储数据的格式,并且很容易解析,因而成为了一种被广泛使用的数据...

    Python处理json字符串转化为字典的简单实现

    总的来说,Python处理JSON字符串转化为字典的过程需要注意JSON格式的规范,即键和字符串值必须使用双引号,并且可以使用`json.loads()`函数来进行转化。对于大量数据,可以通过读取文件内容再进行转化,以适应不同的...

    python:json转换

    总结来说,`trans-json.py`和`trans-json2.py`主要处理JSON数据在Python中的编码和解码,以及转换为不同的输出风格,如“pretty-print”和“单行”模式。通过理解这些基本概念和操作,我们可以更有效地在Python中...

    python 合并json文件代码

    在Python编程中,处理JSON(JavaScript Object Notation)文件是一项常见的任务。JSON是一种轻量级的数据交换格式,因其易于人阅读和编写,同时也易于机器解析和生成,被广泛应用于网络数据传输。当我们需要合并多个...

    Python处理嵌套Json

    利用python处理有嵌套格式的json数据,将二维数组压平并存储到新的json文件中。

    python_json.7z

    本示例中,我们探讨的是如何使用Python来处理JSON文件,特别是加载JSON文件并遍历其中的对象,包括数组。 首先,Python内置了`json`模块,它提供了方便的API来处理JSON数据。在描述中提到的`python_json.7z`压缩包...

    Python-json2csv实现将jsoncsv文件转换工具

    总的来说,Python的json2csv工具提供了一种高效、灵活的方式来处理JSON和CSV之间的数据转换,这对于数据科学家、工程师以及需要处理结构化数据的人来说是一项非常有价值的技能。了解和掌握这一工具的使用,能够极大...

    Python获取json或字典中任意key的value值

    在数据处理或者自动化测试过程中需要对返回的json数据作校验,针对json数据中的单个或多个key进行校验,此时就需要获取json或字典中任意key的value值 数据如下: data = { duringTime: 401, timesPerDay: 10000, ...

Global site tag (gtag.js) - Google Analytics