1.问题

  在遇到json数据的过程中,我们经常需要获取json数据中某个值的操作,如果是用get方法去取比较繁琐,接下来介绍两种方式来取值。

2.jsonpath来格式化处理json数据

2.1介绍

JsonPath是一种信息抽取类库,是从JSON文档中抽取指定信息的工具,提供多种语言实现版本,包括JavaScript、Python、PHP和Java。JsonPath对于JSON来说,就相当于XPATH对于XML。

JsonPath结构清晰,可读性高,复杂度低,非常容易匹配,下表中对应了XPath的用法。

2.2安装

  1. pip安装:
  2. pip install jsonpath
  3.  
  4. 官网文档:http://goessner.net/articles/JsonPath

2.3使用

  1. 使用方法:
  2.  
  3. # 导入
  4. import jsonpath
  5.  
  6. # 结果会以列表形式返回,如下请求接口返回数据提取例子
  7. jsonpath.jsonpath(参数1,参数2)[]
  8.  
  9. # 参数
  10. 参数1:数据对象
  11. 参数2jsonpath表达式
    []:如果有重复的键,需要获取第几个键的值

2.4使用示例:

  1. import jsonpath
  2.  
  3. json_data = {
  4. "resultcode":"200",
  5. "reason":"成功的返回",
  6. "result":
  7. {
  8. "company":"顺丰",
  9. "com":"sf",
  10. "no":"575677355677",
  11. "list":[
  12. {
  13. "datetime":"2013-06-25 10:44:05",
  14. "remark":"已收件",
  15. "zone":"台州市"
  16. },
  17. {
  18. "datetime":"2013-06-25 11:05:21",
  19. "remark":"快件在 台州 ,准备送往下一站 台州集散中心 ",
  20. "zone":"台州市"
  21. }
  22. ],
  23. "status":1
  24. },
  25. "error_code":0
  26. }
  27.  
  28. resultcode = jsonpath.jsonpath(json_data,"$..resultcode")[0]
  29. print("返回的code:",resultcode)
  30. company = jsonpath.jsonpath(json_data, "$..company")[0]
  31. print("快递公司:",company)
  32. remark = jsonpath.jsonpath(json_data,"$..remark")[-1]
  33. print("快递目前到达的地点:",remark)
  34.  
  35. 结果:
  36. 返回的code 200
  37. 快递公司: 顺丰
  38. 快递目前到达的地点: 快件在 台州 ,准备送往下一站 台州集散中心

3.jmespath来格式化处理json数据

jmespath是另一种用来处理json数据的库。

3.1安装

  1. pip安装:
  2. pip install jmespath
  3.  
  4. 官网文档:https://jmespath.org/tutorial.html

3.2基本操作

  1. import jmespath
  2.  
  3. source = {"a": "foo", "b": "bar", "c": "baz"}
  4. result = jmespath.search('b', source)
  5.  
  6. print(repr(result))
  7.  
  8. 结果:
  9. 'bar'

3.3 .操作符

  1. import jmespath
  2.  
  3. source1 = {"a": {"b": {"c": {"d": "value"}}}}
  4. result1 = jmespath.search('a.b.c', source1)
  5. print(repr(result1))
  6.  
  7. 结果:
  8. {'d': 'value'}

3.4下标操作(仅用于数组)

  1. import jmespath
  2.  
  3. source_2 = ["a", "b", "c", "d", "e", "f"]
  4. index_result = jmespath.search("[1]",source_2)
  5. print(repr(index_result))
  6.  
  7. 结果:
  8. 'b'

3.5下标和.操作符混合操作

  1. import jmespath
  2.  
  3. source3 = {"a": {
  4. "b": {
  5. "c": [
  6. {"d": [0, [1, 2]]},
  7. {"d": [3, 4]}
  8. ]
  9. }
  10. }}
  11. result3 = jmespath.search('a.b.c[0].d[1][0]',source3)
  12. print(repr(result3))
  13.  
  14. 结果:
  15. 1

3.6接下来用实际的json数据测试一下

  1. import jmespath
  2.  
  3. json_data = {
  4. "resultcode":"200",
  5. "reason":"成功的返回",
  6. "result":
  7. {
  8. "company":"顺丰",
  9. "com":"sf",
  10. "no":"575677355677",
  11. "list":[
  12. {
  13. "datetime":"2013-06-25 10:44:05",
  14. "remark":"已收件",
  15. "zone":"台州市"
  16. },
  17. {
  18. "datetime":"2013-06-25 11:05:21",
  19. "remark":"快件在 台州 ,准备送往下一站 台州集散中心 ",
  20. "zone":"台州市"
  21. }
  22. ],
  23. "status":1
  24. },
  25. "error_code":0
  26. }
  27.  
  28. resultcode = jmespath.search("resultcode",json_data)
  29. print("返回的code:",resultcode)
  30. company = jmespath.search("result.company",json_data)
  31. print("快递公司:",company)
  32. remark = jmespath.search("result.list[1].remark",json_data)
  33. print("快递目前到达的地点:",remark)
  34.  
  35. 结果:
  36. 返回的code 200
  37. 快递公司: 顺丰
  38. 快递目前到达的地点: 快件在 台州 ,准备送往下一站 台州集散中心

3.7jmespath的其他使用方式

  •切片

  1. import jmespath
  2.  
  3. source_4 = ["a", "b", "c", "d", "e", "f"]
  4. result4 = jmespath.search("[1:3]",source_4)
  5. print(repr(result4))
  6.  
  7. 结果:
  8. ['b', 'c']

  •投影

投影其实就是初始时定义好格式,然后按照格式的方式进行取值。
投影主要包括以下几种:
  List Projections列表投影
  Slice Projections切片投影
  Object Projections对象投影
  Flatten Projections正则投影
  Filter Projections过滤条件投影
注意:取列表用[],取字典用.

  1. 列表和切片投影
  1. import jmespath
  2.  
  3. source5 = {
  4. "people": [
  5. {"first": "James", "last": "d"},
  6. {"first": "Jacob", "last": "e"},
  7. {"first": "Jayden", "last": "f"},
  8. {"missing": "different"}
  9. ],
  10. "foo": {"bar": "baz"}
  11. }
  12. result5 = jmespath.search('people[*].first', source5)
  13. print(result5)
  14.  
  15. 结果:
  16. ['James', 'Jacob', 'Jayden']

对象投影

列表投影是为JSON数组定义的,而对象投影是为JSON对象定义的。

  1. import jmespath
  2.  
  3. source6 = {
  4. "ops": {
  5. "functionA": {"numArgs": 2},
  6. "functionB": {"numArgs": 3},
  7. "functionC": {"variadic": True}
  8. }
  9. }
  10. result6 = jmespath.search('ops.*.numArgs', source6)
  11. print(repr(result6))
  12.  
  13. 结果:
  14. [2, 3]

Filter Projections  带过滤条件投影
格式[? <expression> <comparator> <expression>]
支持 ==, !=, <, <=, >, >=

  1. import jmespath
  2.  
  3. source7 = {
  4. "people": [
  5. {
  6. "general": {
  7. "id": 100,
  8. "age": 20,
  9. "other": "foo",
  10. "name": "Bob"
  11. },
  12. "history": {
  13. "first_login": "2014-01-01",
  14. "last_login": "2014-01-02"
  15. }
  16. },
  17. {
  18. "general": {
  19. "id": 101,
  20. "age": 30,
  21. "other": "bar",
  22. "name": "Bill"
  23. },
  24. "history": {
  25. "first_login": "2014-05-01",
  26. "last_login": "2014-05-02"
  27. }
  28. }
  29. ]
  30. }
  31. result7 = jmespath.search("people[?general.age > `20`].general | [0]", source7)
  32. print(repr(result7))
  33.  
  34. 结果:
  35. {'id': 101, 'age': 30, 'other': 'bar', 'name': 'Bill'}

4.自己写个类来处理json数据

  1. class ExtractData:
  2.  
  3. def traverse_take_field(data,fields,values=[],currentKye=None):
  4. '''
  5. 遍历嵌套字典列表,取出某些字段的值
  6. :param data: 嵌套字典列表
  7. :param fields: 列表,某些字段
  8. :param values: 返回的值
  9. :param currentKye: 当前的键值
  10. :return: 列表
  11. '''
  12. if isinstance(data,list):
  13. for i in data:
  14. ExtractData.traverse_take_field(i,fields,values,currentKye)
  15. elif isinstance(data,dict):
  16. for key,value in data.items():
  17. ExtractData.traverse_take_field(value,fields,values,key)
  18. else:
  19. if currentKye in fields:
  20. values.append(data)
  21. return values
  22.  
  23. if __name__ == '__main__':
  24. json_data = {
  25. "resultcode":"200",
  26. "reason":"成功的返回",
  27. "result":{
  28. "company":"顺丰",
  29. "com":"sf",
  30. "no":"575677355677",
  31. "list":[
  32. {
  33. "datetime":"2013-06-25 10:44:05",
  34. "remark":"已收件",
  35. "zone":"台州市"
  36. },
  37. {
  38. "datetime":"2013-06-25 11:05:21",
  39. "remark":"快件在 台州 ,准备送往下一站 台州集散中心 ",
  40. "zone":"台州市"
  41. }
  42. ],
  43. "status":1
  44. },
  45. "error_code":0
  46. }
  47. resultcode = ExtractData.traverse_take_field(data=json_data,fields="resultcode")
  48. print("返回的code:",resultcode)
  49.  
  50. 结果:
  51. 返回的code ['200']

目前自己写的这个类还不完善,有以下几个缺点:

1、只能获取最底层的值

2、重复的键例如:remark,获取值后,会把所有的值都获取出来。

3、对于包含的键,无法做出区分,列如:想要获取键company的值,会吧键com的值也一起获取出来。

等有时间可以继续完善。

Python格式化处理json数据的方式的更多相关文章

  1. Python格式化输出的三种方式

    Python格式化输出的三种方式 一.占位符 程序中经常会有这样场景:要求用户输入信息,然后打印成固定的格式比如要求用户输入用户名和年龄,然后打印如下格式:My name is xxx,my age ...

  2. (数据科学学习手札125)在Python中操纵json数据的最佳方式

    本文示例代码及文件已上传至我的Github仓库https://github.com/CNFeffery/DataScienceStudyNotes 1 简介 在日常使用Python的过程中,我们经常会 ...

  3. 【转】让浏览器格式化显示JSON数据之chrome jsonView插件安装

    jsonView 用来让Chrome浏览器能格式化的显示JSON数据. 以上是网上找的方式,且试验成功! 步骤: 1.打开 https://github.com : 2.搜索 jsonView 链接: ...

  4. 8种json数据查询方式

    你有没有对“在复杂的JSON数据结构中查找匹配内容”而烦恼.这里有8种不同的方式可以做到: JsonSQL JsonSQL实现了使用SQL select语句在json数据结构中查询的功能. 例子: ? ...

  5. Python爬虫之三种数据解析方式

    一.引入 二.回顾requests实现数据爬取的流程 指定url 基于requests模块发起请求 获取响应对象中的数据 进行持久化存储 其实,在上述流程中还需要较为重要的一步,就是在持久化存储之前需 ...

  6. 3中转换JSON数据的方式

    一:前言 来公司一个星期,把最近做的东西梳理下,并把觉得有必要的知识点记载下,现在传数据很多都是用JSON来传数据,所以我就找了集中传json的方式,其实是有五种的,但是有一个我没有用过,太陌生了,上 ...

  7. jQuery格式化显示json数据

    一.概述 JSONView 在gitlab上面,有一个jQuery JSONView插件,地址为:https://github.com/yesmeck/jquery-jsonview demo地址:h ...

  8. vue项目中使用插件将字符串装化为格式化的json数据(可伸缩)

    插件地址:https://www.npmjs.com/package/vue-json-viewer 第一步:安装vue-json-viewer插件 $ npm install vue-json-vi ...

  9. c#处理3种json数据的方式

    原文出处:http://www.jb51.net/article/48027.htm 一.C#处理简单json数据 json数据: {"result":"0", ...

随机推荐

  1. RHCSA 复习

    1.用户 # -->当前用户为root用户 $ -->当前用户为普通用户 [root@fafa ~]# su - 用户   ----切换用户 2.查看.修改主机名: ***保存在/etc/ ...

  2. Excel 冻结窗口

    1.冻结前五行 鼠标选中第六行,点击视图----> 冻结窗口 ----> 冻结拆分窗口 2.冻结第一列窗口 鼠标选中第1列,点击视图----> 冻结窗口 ----> 冻结首列窗 ...

  3. spring-boot 使用hibernate validation对参数进行优雅的校验

    springboot天生支持使用hibernate validation对参数的优雅校验,如果不使用它,只能对参数挨个进行如下方式的手工校验,不仅难看,使用起来还很不方便: if(StringUtil ...

  4. 配置简单的拦截器java中

    springMVC.xml文件中==== <!-- 拦截器 --> <mvc:interceptors> <mvc:interceptor> <mvc:map ...

  5. [leetcode]725. Split Linked List in Parts链表分块

    思路很简单  按时链表的题做起来很容易犯小错误,思维要缜密 还要多练习啊 做之前最好画算法框图 public ListNode[] splitListToParts(ListNode root, in ...

  6. 【wp】2020XCTF_逆向

    前几天的XCTF最后一场终于打完了,三场比赛下来对逆向部分的大概感觉是从第一场的啥都不会做(一道lua+一道apk)到后来的终于能有参与度,至少后两场的题目都是pc逆向,虽然特殊架构但好歹能做(tcl ...

  7. Queue的使用说明

    普通的Queue.Queue是单个进程间的队列,不同进程不能共享:multiprocessing.Queue()是不同进程间使用的,可以共享:如果是进程池的话需要使用multiprocessing.M ...

  8. C# 串口连接的读取与发送

    一.串口连接的打开与关闭 串口,即COM口,在.NET中使用 SerialPort 类进行操作.串口开启与关闭,是涉及慢速硬件的IO操作,频繁打开或关闭会影响整体处理速度,甚至导致打开或关闭串口失败. ...

  9. android stdio 打包

    1.Build -> Generate Signed APK...,打开如下窗口 2.假设这里没有打过apk包,点击Create new,窗口如下 这里只要输入几个必要项 Key store p ...

  10. TextView上下滚动

    public class AutoTextView extends TextSwitcher implements ViewFactory { private float mHeight; priva ...