JSON 原始原理 全!!

JSON简介

  • JAVAScript Object Notation是一种轻量级的数据交换格式
  • 具有良好的可读和便于快速编写的特性。
  • 业内主流技术为其提供了完整的解决方案(有点类似于正则表达式 ,获得了当今大部分语言的支持)
  • JSON采用兼容性很高的文本格式,同时也具备类似于C语言体系的行为。 – Json.org
  • JSON作为数据是目前网络中主流的数据传输格式之一,应用十分广泛,说是使用率达到99%一点也不勉强

JSON支持的数据类型

我们要学习使用JSON解析,必须对JSON解析的规则原理有深刻的认识和了解,然后才知道它的一个实现原理
JSON里面的数据是以一种键值对的方式存在
(”key”:”value”)中值的类型可以是下面数据类型中的任意一种:
1. 数字(整数或浮点数)
2. 逻辑值(true 或 false)
3. 字符串(在双引号中)
4. 数组(在方括号中)
5. 函数
6. 对象(在大括号中)
7. null

JSON语法规则

JSON的语法规则非常的简单,就是使用
大括号’{}’,
中括号’[]’,
逗号’,’,
冒号’:’,
双引号’“”’。

数据类型:
嵌套对象、数组、字符串、数字、布尔值或空值。

我们在JSON解析中只有三中情况出现
1.{} 解析’大括号’类型
2. [ ] 解析是’中括号’类型
3. 其实只有两种,那第三种则是1与2的组合方法即”{’name’:’李书豪’ ,’hobby’:[‘编程’,’电竞’,’睡觉’]}”那么下面分别来看一些这三种类型以及解析

JSON基本语法与图例

  • Object(对象类型)
    • 用{ }包含一系列无序的key–Value键值对表示,其中Key和Value之间用冒号分割,每个key-value之间用逗号分割。
    • 比如:这里写图片描述
  • Array(数组类型)
    • 使用[ ]包含所有元素,每个元素用逗号分隔,元素可以是任意的值
    • 比如:这里写图片描述
  • 组合形
    • 这里写图片描述
      这里写图片描述

JSON数据解析

  • JSON解析一定要掌握的两条规则:

    • 1.如果看到是{ }–>使用JSONObject
    • 2.如果看到的[ ]–>使用JSONArray解析
  • 掌握了JSON的数据类型和基本语法后,下面我们将对JSON的各种语法类型进行详细解析(注意掌握两条规则的使用,掌握了JSON解析就那么回事)

纯对象(Object)的解析{ }:


 
 
  1. import org.json.JSONException;
  2. import org.json.JSONObject;
  3. /**
  4. * JSON-->纯对象(Object)的解析
  5. *
  6. * 注:我们在eclipse里面操作JSON解析的时候需要第三方jar包的支持
  7. * @author sKy°
  8. * @date 2016-5-8
  9. * @version 1.0
  10. */
  11. public class Json01 {
  12. public static void main(String[] args) {
  13. // 编辑一个我们要解析的数据对象
  14. // 根据JSON的官方定义,键,加"",值,如果是字符串,就加"",其他不加。
  15. String json= "{'name':'李书豪','age':24}";
  16. try {
  17. // 创建JSON解析对象(两条规则的体现:大括号用JSONObject,注意传入数据对象)
  18. JSONObject obj = new JSONObject(json);
  19. // obj.后面有各种数据类型,根据对象来选择使用的数据类型
  20. String name = obj.getString( "name");
  21. // 同理如上,这里的age为Int类型,我们就用对应的类型进行解析
  22. int age = obj.getInt( "age");
  23. // 最后输出到控制台
  24. System.out.println(name+ "<--->"+age);
  25. } catch (JSONException e) {
  26. e.printStackTrace();
  27. }
  28. }
  29. }

这里写图片描述

纯数组(Array)的解析{ }:

 
 
  1. import org.json.JSONArray;
  2. import org.json.JSONException;
  3. /**
  4. * 对纯数组Aarry的解析
  5. * @author sKy°
  6. * @date 2016-5-8
  7. * @version 1.0
  8. */
  9. public class Json02 {
  10. public static void main(String[] args) {
  11. // 编辑一个我们要解析的数据对象
  12. String json= "['天津冷','北京暖','东京热','南京凉']";
  13. try {
  14. // 创建JSON解析对象(两条规则的体现:中括号用JSONArray,注意传入数据对象)
  15. JSONArray jArray = new JSONArray(json);
  16. // 取得数组长度
  17. int length = jArray.length();
  18. // 回想数组的取值的方式? --->for循环遍历数组--->得到值
  19. for ( int i = 0; i < length; i++) {
  20. // 根据解析的数据类型使用该类型的get方法得到该值,打印输出
  21. String string = jArray.getString(i);
  22. System.out.print(string+ ",");
  23. }
  24. } catch (JSONException e) {
  25. // TODO: handle exception
  26. }
  27. }
  28. }

这里写图片描述

组合类型的解析(一):
  • 例子: String json=”{‘name’:’李书豪’,’girlFriend’:{‘name’:’高圆圆’,’age’:18}}”;
  • 分析: 我们首先是解析外面的大括号的对象,然后,通过girlfFriend,获取到对应的被包含的里面大括号对象。所以这里我们需要建立一个类,封装对应的数据字段,根据setName ,setAge的方式在去得到对应的值

 
 
  1. /**
  2. * 创建一个Person用于接收解析数据,封装对应字段
  3. * @author sKy°
  4. * @date 2016-5-8
  5. * @version 1.0
  6. */
  7. public class Person {
  8. // 分析我们要解析的对象,根据解析对象的属性值去创建对应的属性值
  9. // 根据分析我们所要解析的对象,两条属性 1.name(String类型) 2.是girlFrien(类类型,意味着还需要在类中去嵌套一个类(创建类部类也可))
  10. // 封装字段
  11. private String name;
  12. private GirlFriend girlFriend; //类类型
  13. // setter getter方法
  14. public String getName() {
  15. return name;
  16. }
  17. public void setName(String name) {
  18. this.name = name;
  19. }
  20. public GirlFriend getGirlFriend() {
  21. return girlFriend;
  22. }
  23. public void setGirlFriend(GirlFriend girlFriend) {
  24. this.girlFriend = girlFriend;
  25. }
  26. // toString方法用于控制台输出
  27. @Override
  28. public String toString() {
  29. return "Person [name=" + name + ", girlFriend=" + girlFriend + "]";
  30. }
  31. }
  32. // 为了方便咱们看,这里就直接在下面创建了一个GirlFriend这个类
  33. class GirlFriend{
  34. // 根据对象属性值,创建对应的值
  35. private String name;
  36. private int age;
  37. // setter getter方法
  38. public String getName() {
  39. return name;
  40. }
  41. public void setName(String name) {
  42. this.name = name;
  43. }
  44. public int getAge() {
  45. return age;
  46. }
  47. public void setAge(int age) {
  48. this.age = age;
  49. }
  50. // toString方法用于控制台输出
  51. @Override
  52. public String toString() {
  53. return "GirlFriend [name=" + name + ", age=" + age + "]";
  54. }
  55. }

开始解析:

 
 
  1. import org.json.JSONException;
  2. import org.json.JSONObject;
  3. /**
  4. * 组合数据类型的解析--->对象嵌套对象类型
  5. * @author sKy°
  6. * @date 2016-5-8
  7. * @version 1.0
  8. */
  9. public class Json03 {
  10. public static void main(String[] args) {
  11. // 编辑一个我们要解析的数据对象
  12. // 分析: 应该先解析外面的大的对象,然后,通过girlfFriend,获取到对应的被包含的对象。
  13. // 所以这里我们需要建立一个类,封装对应的数据字段,根据setName ,setAge的方式在去得到对应的值
  14. String json= "{'name':'李书豪','girlFriend':{'name':'高圆圆','age':18}}";
  15. try {
  16. // 1.创建JSON解析对象(两条规则的提现:大括号用JSONObject,注意传入数据对象)
  17. JSONObject jObj = new JSONObject(json);
  18. // 2.实例化Person对象获取对应的值--->这里是获得外面大括号{}的name值 思考?里面{}如何获得?
  19. Person per= new Person();
  20. String name = jObj.getString( "name");
  21. per.setName(name);
  22. // 3.分析:里面{}是嵌套在外面大括号类的所以我们解析的对象是通过外面大括号去取得里面大括号值,注意看
  23. //取得对应里面大括号的girlFriend,取得name值,赋值给girlFriend对象
  24. GirlFriend girlFriend= new GirlFriend();
  25. JSONObject jObj1 = jObj.getJSONObject( "girlFriend");
  26. String gfName = jObj1.getString( "name");
  27. girlFriend.setName(gfName);
  28. // 获得age值并赋值
  29. int gfAge = jObj1.getInt( "age");
  30. girlFriend.setAge(gfAge);
  31. // 通过set把girlFriend的值赋Person 用于toString的输出,不然为空
  32. per.setGirlFriend(girlFriend);
  33. // 输出
  34. System.out.println(per);
  35. } catch (JSONException e) {
  36. e.printStackTrace();
  37. }
  38. }
  39. }

这里写图片描述
小结: {[ {},{} ]}–>思路:第一步看到大括号:JSONObject去解,创建好对应里面的属性的值;第二步看到中括号:JSONArray去解析 对应创建好对应里面的属性值;第三步中括号里面的{},又是一个JSONObject。思路大致如此,强调注意的是,设置的属性值setXxx getXxx必须要和去获得值名称一致,不然会出错!!

组合类型的解析(二):
下面我们来解析一个略为复杂的JSON数据
要解析的数据如下:


 
 
  1. {
  2. 'desc': 'OK',
  3. 'status': 1000,
  4. 'data': {
  5. 'wendu': '20',
  6. 'ganmao': '相对于今天将会出现大幅度降温,易发生感冒,请注意适当增加衣服,加强自我防护避免感冒。',
  7. 'forecast': [
  8. {
  9. 'fengxiang': '北风',
  10. 'fengli': '3-4级',
  11. 'high': '高温 27℃',
  12. 'type': '中雨',
  13. 'low': '低温 19℃',
  14. 'date': '6日星期五'
  15. },
  16. {
  17. 'fengxiang': '北风',
  18. 'fengli': '微风级',
  19. 'high': '高温 23℃',
  20. 'type': '大雨',
  21. 'low': '低温 17℃',
  22. 'date': '7日星期六'
  23. },
  24. {
  25. 'fengxiang': '北风',
  26. 'fengli': '微风级',
  27. 'high': '高温 26℃',
  28. 'type': '小雨',
  29. 'low': '低温 17℃',
  30. 'date': '8日星期天'
  31. },
  32. {
  33. 'fengxiang': '南风',
  34. 'fengli': '微风级',
  35. 'high': '高温 27℃',
  36. 'type': '多云',
  37. 'low': '低温 15℃',
  38. 'date': '9日星期一'
  39. },
  40. {
  41. 'fengxiang': '南风',
  42. 'fengli': '微风级',
  43. 'high': '高温 29℃',
  44. 'type': '多云',
  45. 'low': '低温 16℃',
  46. 'date': '10日星期二'
  47. }
  48. ],
  49. 'yesterday': {
  50. 'fl': '微风',
  51. 'fx': '北风',
  52. 'high': '高温 33℃',
  53. 'type': '阴',
  54. 'low': '低温 22℃',
  55. 'date': '5日星期四'
  56. },
  57. 'aqi': '58',
  58. 'city': '成都'
  59. }
  60. }

因为数据略大,不方便咱们看,这里给大家提供一个JSON在线解析工具http://json.phpddt.com/ 这是JSON在线高亮解析 ,可以很好的帮助咱们进行解析分析。下面是我用网页解析好的图片,可以思考下步骤(记住两条规则)
这里写图片描述

分析:
这里写图片描述
一:第一个大括号(JSONObject){”desc”: “status”: “data”}
二:大括号里面有一个大括号(JSONObject){”wendu”: “20”, “ganmao”: “forecast”: “yesterday”: “aqi”: “city”: }
三:第二个大括号里面有两个对象 1.数组形(JSONArray) 2.对象形( JSONObject )
而数组形里面又套有数组的对象{} 。这就需要咱们在解析的时候需要很细致的去创建对应的属性值,JSON解析并不难,而难受的地方就提现在对类的创建中,只要够细心也超简单!

开始封装字段


 
 
  1. import java.util.List;
  2. /**
  3. * 对应的字段的封装
  4. * @author sKy°
  5. * @date 2016-5-6
  6. * @version 1.0
  7. */
  8. public class Weather {
  9. // 外面大括号的字段封装 setter getter toString
  10. public String desc;
  11. public int status;
  12. public Data data;
  13. @Override
  14. public String toString() {
  15. return "Weather [desc=" + desc + ", status=" + status + ", data="
  16. + data + "]";
  17. }
  18. }
  19. class Data{
  20. // 里面大括号的字段封装 setter getter toString
  21. // 该类中包含有数组形和对象形,需要一并的封装在里面
  22. public String wendu;
  23. public String ganmao;
  24. public List<Forecast> forecast;
  25. public Yesterday yesterday;
  26. public String aqi;
  27. public String city;
  28. @Override
  29. public String toString() {
  30. return "Data [wendu=" + wendu + ", ganmao=" + ganmao + ", forecast="
  31. + forecast + ", yesterday=" + yesterday + ", aqi=" + aqi
  32. + ", city=" + city + "]";
  33. }
  34. }
  35. class Forecast{
  36. // 数组里面的大括号类型字段的封装
  37. public String fengxiang;
  38. public String fengli;
  39. public String high;
  40. public String type;
  41. public String low;
  42. public String date;
  43. @Override
  44. public String toString() {
  45. return "Forecast [fengxiang=" + fengxiang + ", fengli=" + fengli
  46. + ", high=" + high + ", type=" + type + ", low=" + low
  47. + ", date=" + date + "]";
  48. }
  49. }
  50. class Yesterday{
  51. // 最后{}的字段封装
  52. public String fl;
  53. public String fx;
  54. public String high;
  55. public String type;
  56. public String low;
  57. public String date;
  58. @Override
  59. public String toString() {
  60. return "Yesterday [fl=" + fl + ", fx=" + fx + ", high=" + high
  61. + ", type=" + type + ", low=" + low + ", date=" + date + "]";
  62. }
  63. }

开始解析:

 
 
  1. import java.util.ArrayList;
  2. import java.util.List;
  3. import org.json.JSONArray;
  4. import org.json.JSONException;
  5. import org.json.JSONObject;
  6. /**
  7. * 组合类型二的解析
  8. * @author sKy°
  9. * @date 2016-5-6
  10. * @version 1.0
  11. */
  12. public class Test01 {
  13. public static void main(String[] args) throws Exception {
  14. //要解析的对象
  15. String json= "{ 'desc': 'OK', 'status': 1000, 'data': { 'wendu': '20', 'ganmao': '相对于今天将会出现大幅度降温,易发生感冒,请注意适当增加衣服,加强自我防护避免感冒。', 'forecast': [ { 'fengxiang': '北风', 'fengli': '3-4级', 'high': '高温 27℃', 'type': '中雨', 'low': '低温 19℃', 'date': '6日星期五' }, { 'fengxiang': '北风', 'fengli': '微风级', 'high': '高温 23℃', 'type': '大雨', 'low': '低温 17℃', 'date': '7日星期六' }, { 'fengxiang': '北风', 'fengli': '微风级', 'high': '高温 26℃', 'type': '小雨', 'low': '低温 17℃', 'date': '8日星期天' }, { 'fengxiang': '南风', 'fengli': '微风级', 'high': '高温 27℃', 'type': '多云', 'low': '低温 15℃', 'date': '9日星期一' }, { 'fengxiang': '南风', 'fengli': '微风级', 'high': '高温 29℃', 'type': '多云', 'low': '低温 16℃', 'date': '10日星期二' } ], 'yesterday': { 'fl': '微风', 'fx': '北风', 'high': '高温 33℃', 'type': '阴', 'low': '低温 22℃', 'date': '5日星期四' }, 'aqi': '58', 'city': '成都' } }";
  16. Weather wea= new Weather();
  17. // 首先看到的是一个{}所以用JSON Object来进行解析
  18. // 获得外部的Weather
  19. JSONObject obj = new JSONObject(json);
  20. String desc = obj.getString( "desc");
  21. int status = obj.getInt( "status");
  22. wea.status=status;
  23. wea.desc=desc;
  24. // 获得内部Data的数据
  25. JSONObject obj1 = obj.getJSONObject( "data");
  26. Data data= new Data();
  27. data.wendu=obj1.getString( "wendu");
  28. data.ganmao=obj1.getString( "ganmao");
  29. data.aqi=obj1.getString( "aqi");
  30. data.city=obj1.getString( "city");
  31. wea.data=data;
  32. List<Forecast> forecasts= new ArrayList<>();
  33. // 获取forecast数组
  34. JSONArray jArr = obj1.getJSONArray( "forecast");
  35. for ( int i = 0; i < jArr.length(); i++) {
  36. JSONObject obj2 = jArr.getJSONObject(i);
  37. Forecast forecast= new Forecast();
  38. forecast.date=obj2.getString( "date");
  39. forecast.fengxiang=obj2.getString( "fengxiang");
  40. forecast.high=obj2.getString( "high");
  41. forecast.low=obj2.getString( "low");
  42. forecast.fengli=obj2.getString( "fengli");
  43. forecast.type=obj2.getString( "type");
  44. forecasts.add(forecast);
  45. }
  46. data.forecast=forecasts;
  47. JSONObject obj3 = obj1.getJSONObject( "yesterday");
  48. Yesterday yesterday= new Yesterday();
  49. yesterday.fl=obj3.getString( "fl");
  50. yesterday.fx=obj3.getString( "fx");
  51. yesterday.high=obj3.getString( "high");
  52. yesterday.type=obj3.getString( "type");
  53. yesterday.low=obj3.getString( "low");
  54. yesterday.date=obj3.getString( "date");
  55. data.yesterday=yesterday;
  56. // 输出字段
  57. System.out.println(wea);
  58. }

解析结果:

这里写图片描述

结语: 对于JSON解析个人的粗浅看法,
1.首先是对JSON数据的一个分析
2.其次是掌握JSON一些技巧(两条规则–对象形JSONObject ,数组形JSONArray)
3.而后是对对应的属性值进行对应的字段封装建立对应的类(分析要细心,思路要清晰,程序这行需要有耐心不能浮躁)
4.而后是解析中要有明确的思路

(以上只是一个JSON初步的解析,但JSON解析的大致思路如此,后面有http套用的,无非也就把下载的文件转为JSON对象,后面解析思路也是如此,写的不好的地方大家包涵!有啥问题,欢迎留言!)


  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: @jsonformat 是一个 Java 注解,用于格式化 JSON 字符串和 Java 对象之间的转换。它的实现原理如下: 1. 首先,@jsonformat 注解会在编译时进行解析,获取注解中的配置信息。 2. 当需要进行 JSON 字符串和 Java 对象之间的转换时,程序会先检查对象是否有 @jsonformat 注解。 3. 如果对象有 @jsonformat 注解,程序会根据注解中的配置,选择相应的转换方法。 4. 对于将 Java 对象转换为 JSON 字符串的情况,程序会根据注解中的配置,将对象的属性值转换为对应的 JSON 字符串格式。例如,可以配置日期时间格式、数字格式、字符串格式等。 5. 对于将 JSON 字符串转换为 Java 对象的情况,程序会根据注解中的配置,将 JSON 字符串的键值对转换为对象的属性。例如,可以配置日期时间格式、数字格式、字符串格式等。 6. @jsonformat 注解还可以用于指定属性的排列顺序,以及是否忽略某些属性的转换。 总的来说,@jsonformat 注解的实现原理是通过解析注解中的配置信息,在转换 JSON 字符串和 Java 对象时,根据配置信息选择合适的转换方法,并对属性值进行格式化处理。这样可以方便地控制 JSON 字符串和 Java 对象之间的转换过程,提高代码的可读性和可维护性。 ### 回答2: @jsonformat 是一个用于将json数据格式化的注解,它是使用Java语言开发的。@jsonformat 可以应用在类、属性或方法上。 @jsonformat 的实现原理主要涉及两个方面:反射和JSON解析。 首先,通过使用反射,程序可以在运行时获取类、属性或方法的相关信息。当在类上使用@jsonformat 注解时,程序通过反射获取类的属性列表,并对属性进行格式化处理。当在属性上使用@jsonformat 注解时,程序获取属性的值,并对该值进行格式化处理。当在方法上使用@jsonformat 注解时,程序通过反射获取方法的返回类型,并对返回值进行格式化处理。 其次,@jsonformat 通过使用JSON解析工具,将原始json数据格式化成特定的形式。JSON解析工具可以将原始json数据解析成对象的形式,或者将对象转化为json格式。@jsonformat 的实现原理就在于调用JSON解析工具,将原始json数据格式化成符合注解定义的格式。 总的来说,@jsonformat 的实现原理是通过反射获取类、属性或方法的相关信息,并通过JSON解析工具将原始json数据格式化成符合注解定义的格式。在实际使用中,@jsonformat 可以帮助程序员更加方便地对json数据进行格式化处理,提高了编码效率。 ### 回答3: @jsonformat 是一个用于将 JSON 格式化的 Java 注解。它的实现原理如下: 首先,@jsonformat 是通过使用 Java 的反射机制实现的,它可以在运行时获取被注解的字段信息。 当需要将一个对象转换成 JSON 字符串时,在序列化过程中会遍历对象的所有字段。如果某个字段被 @jsonformat 注解标记,则根据注解的配置,对该字段进行相应的格式化处理。 @jsonformat 注解包含了一些常用的配置选项,例如日期格式化、数字格式化等。当需要对日期字段进行格式化时,可以在注解中指定日期的格式。在序列化过程中,解析器会根据配置的格式将日期转换成指定的字符串格式。 对于数字字段,可以指定数字的格式,例如保留小数位数、千位分隔符等。解析器会根据配置的格式对数字进行相应的格式化处理。 除了日期和数字字段之外,@jsonformat 还支持其他类型的格式化,例如枚举类型、集合类型等。对于枚举类型,可以指定字段的展示方式(如按枚举值展示还是按枚举名称展示)。对于集合类型,可以指定字段元素的展示方式(如按照指定的顺序展示还是按照元素的默认顺序展示)。 总之,@jsonformat 注解的实现原理是通过反射机制在字段序列化过程中对字段进行格式化处理。这使得我们可以定义和配置各种类型的格式化方式,以满足不同场景下的需求。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值