程序员最近都爱上了这个网站  程序员们快来瞅瞅吧!  it98k网:it98k.com

本站消息

站长简介/公众号

  出租广告位,需要合作请联系站长

+关注
已关注

分类  

暂无分类

标签  

暂无标签

日期归档  

2024-11(1)

荐(十四)Python中级知识-JSON模块

发布于2020-03-18 10:52     阅读(1818)     评论(0)     点赞(8)     收藏(1)


1、概述

json数据格式也是比较常用数据传输格式,各类编程语言都有对JSON字符串与对象的各种转换,JSON数据转化在java中经常用到,在java中有自带JSONObject类来进行处理。在Python3中提供了json模块来进行处理。使用json模块之前先导入它:

import json

2、常用函数

函数名 描述
json.dump(obj,fp) 使用这个 转换表 将 obj 序列化为 JSON 格式化流形式的 fp (支持 .write() 的 file-like object)。即:将对象转换成文件流的形式
json.dumps(obj) 使用这个 转换表 将 obj 序列化为 JSON 格式的 str。 其参数的含义与 dump() 中的相同。即:将对象转换成JSON字符串
json.load(fp) 使用这个 转换表 将 fp (一个支持 .read() 并包含一个 JSON 文档的 text file 或者 binary file) 反序列化为一个 Python 对象。即:将文件流转换成对象
json.loads(s) 使用这个 转换表 将 s (一个包含 JSON 文档的 str, bytes 或 bytearray 实例) 反序列化为 Python 对象。即:将JSON字符串转换成对象
decode(s) 返回 s 的 Python 表示形式(包含一个 JSON 文档的 str 实例)。如果给定的 JSON 文档无效则将引发 JSONDecodeError。
encode(o) 返回 Python o 数据结构的 JSON 字符串表达方式。

在上表中常用函数的参数只列出了必填参数,而一些缺省参数没有列出来。

json.loads函数完整格式:

json.loads(s, *, cls=None, object_hook=None, parse_float=None,
parse_int=None, parse_constant=None, object_pairs_hook=None, **kw)

参数说明:

在这里插入图片描述

json.dumps函数完整格式

json.dumps(obj, *, skipkeys=False, ensure_ascii=True,
check_circular=True, allow_nan=True, cls=None, indent=None,
separators=None, default=None, sort_keys=False, **kw)

参数说明

在这里插入图片描述

3、应用场景

3.1、字典与JSON对象互转

举个例子:

import json

# 创建一个字典
dic = {'name': '小明', 'age': 18}
print("转之前的字典:", dic)

# 如果 ensure_ascii 是 true (即默认值),输出保证将所有输入的非 ASCII 字符转义。如果 ensure_ascii 是 false,这些字符会原样输出。
# 字典转换成json对象
jsonObj = json.dumps(dic,ensure_ascii=False)

print("JSON对象:", jsonObj)

# json对象转换成字典
redic = json.loads(jsonObj)

print("转之后的字典:", jsonObj)

注意上述代码中用到 了ensure_ascii = False这个标记参数。

如果 ensure_ascii 是 true (即默认值),输出保证将所有输入的非 ASCII 字符转义。如果 ensure_ascii 是 false,这些字符会原样输出。

输出:
转之前的字典: {'name': '小明', 'age': 18}
JSON对象: {"name": "小明", "age": 18}
转之后的字典: {"name": "小明", "age": 18}

3.2、列表与JSON对象互转

直接使用

list=[1,2,3,4]

这种结构是不能直接转换成JSON对象的,但是有另外一种结构即list中包含字典,如:

list=[{"id": "1", "title": "测试标题1", "subTitle": "子标题1"},{"id": "2", "title": "测试标题2", "subTitle": "子标题2"}]

这种结构是转换成json对象的。

举个例子:
import json

# 创建一个字典
dic = {'name': '小明', 'age': 18}
dic2 = {'name': '小花', 'age': 16}

print("转之前的字典:", dic)
print("转之前的字典:", dic2)

list=[]
list.append(dic)
list.append(dic2)

print("转之前的列表:",list)


# 如果 ensure_ascii 是 true (即默认值),输出保证将所有输入的非 ASCII 字符转义。如果 ensure_ascii 是 false,这些字符会原样输出。
# 列表转换成json对象
jsonObj = json.dumps(list,ensure_ascii=False)

print("JSON对象:", jsonObj)

# json对象转换成列表
reList = json.loads(jsonObj)

print("转之后的列表:", jsonObj)

输出:
转之前的字典: {'name': '小明', 'age': 18}
转之前的字典: {'name': '小花', 'age': 16}
转之前的列表: [{'name': '小明', 'age': 18}, {'name': '小花', 'age': 16}]
JSON对象: [{"name": "小明", "age": 18}, {"name": "小花", "age": 16}]
转之后的列表: [{"name": "小明", "age": 18}, {"name": "小花", "age": 16}]

3.3、class类与JSON对象互转

class类转JSON对象或者字符串转JSON对象再转类对象这些都是在实际项目开发中频繁使用的。所以下面的例子做了这些实践。当然还有一些更多的办法,大家可以自行扩展。

举个例子:
import json


# 声明一个类
class Student:

    @property
    def name(self):
        return self.__name

    @name.setter
    def name(self, name):
        self.__name = name

    @property
    def age(self):
        return self.__age

    @age.setter
    def age(self, age):
        self.__age = age


# 定义一个独立的接收方法 通过 object_hook 调用
def handle(dic):
    s = Student()
    s.name = dic['_Student__name']
    s.age = dic['_Student__age']
    return s


std = Student()
std.name = "小明"
std.age = 18

print("原对象:", std)
# 将class类转成json对象  ,在转换之前需要先序列化类(类实例.__dict__可序列化类),不序列化会报错 TypeError: Object of type 'Student' is not JSON serializable
jsonObj = json.dumps(std.__dict__, ensure_ascii=False)

print("JSON对象:", jsonObj)

# encode & decode 用法
encodeStr = json.JSONEncoder().encode(jsonObj)
print("JSON对象转换成JSON字符串:", encodeStr)
decodeStr = json.JSONDecoder().decode(encodeStr)
print("JSON字符串转换成JSON对象:", decodeStr)

# 将json对象转化成类对象
std2 = json.loads(jsonObj, object_hook=handle)

print("std2是否属于Student类的实例:", isinstance(std2, Student))

# 输出类对象的属性值
print(std2.name, std2.age)

# 往当前目录下的data.json 这个文件 写入 std2 类对象的数据,如果没有这个文件会自动创建
with open('data.json', 'w', encoding="utf-8") as f:
    json.dump(std2.__dict__, f, ensure_ascii=False)
    # 用with open 语句 f.flush() 与 f.close()语句可以不用写了

# 读取data.json文件内容
with open('data.json', 'r', encoding="utf-8") as f:
    data = json.load(f)
    print("从data.json文件中读取json字符串,并转化为JSON对象:", data)

温馨提示

  • 类对象转JSON对象时,需要先序列化类,可通过[类实例.dict]的方式进行序列化,若不序列化类,则会报错TypeError:
    Object of type ‘Student’ is not JSON serializable。
  • JSON对象转换成Python对象后返回的其实是一个字典类型,我们需要将字典的键值设置到对应的类对象的属性上,然后再返回这个类对象,就可以直接使用了。
输出:
原对象: <__main__.Student object at 0x0000023F75D74898>
JSON对象: {"_Student__name": "小明", "_Student__age": 18}
JSON对象转换成JSON字符串: "{\"_Student__name\": \"\u5c0f\u660e\", \"_Student__age\": 18}"
JSON字符串转换成JSON对象: {"_Student__name": "小明", "_Student__age": 18}
std2是否属于Student类的实例: True
小明 18
从data.json文件中读取json字符串,并转化为JSON对象: {'_Student__name': '小明', '_Student__age': 18}

4、总结

关于 json.JSONEncoder().encode(jsonObj)函数的直白理解:JSON对象转换成JSON字符串;
关于 json.JSONDecoder().decode(encodeStr)函数的直白理解:JSON字符串转换成JSON对象;
关于json.dump&json.load两个不带s的函数这里非常有用,可以想象的是做一些缓存操作,预先把缓存json数据存储到本地文件中,然后再读取出来使用,特别注意的是使用中文的时候要记得设置编码为utf-8;
注意本文使用了==with open ==语句 ,所以 f.flush() 与 f.close()语句可以不用写了,原因是:
If a file descriptor is given, it is closed when the returned I/O object is closed, unless closefd is set to False. with open 语句默认的这个缺省参数[closefd] 为[True],会返回值的时候会自动去关闭文件操作。

写了一天才有此篇文章,若有不当之处请评论区斧正。

参考链接:
(1)、官方文档地址:JSON 编码和解码器

原文链接:https://blog.csdn.net/huangbin123/article/details/104916059



所属网站分类: 技术文章 > 博客

作者:一切都会好起来over

链接:https://www.pythonheidong.com/blog/article/265187/ddbed6aebef2b8babddc/

来源:python黑洞网

任何形式的转载都请注明出处,如有侵权 一经发现 必将追究其法律责任

8 0
收藏该文
已收藏

评论内容:(最多支持255个字符)