天天看點

小東吖 之 java JSON解析

一.JSON簡介

AVAScript Object Notation是一種輕量級的資料交換格式

具有良好的可讀和便于快速編寫的特性。

業内主流技術為其提供了完整的解決方案(有點類似于正規表達式 ,獲得了當今大部分語言的支援)

JSON采用相容性很高的文本格式,同時也具備類似于C語言體系的行為。 – Json.org

JSON作為資料是目前網絡中主流的資料傳輸格式之一,應用十分廣泛,說是使用率達到99%一點也不勉強

二.JSON文法

JSON 文法

作用: JSON文本是類似XML文本檔案,用來儲存和傳輸資料資訊的的媒介

注: JSON同XML一樣,不僅可以通過響應檔案作為資料的載體,也可以通過滿足文法字元串作為對應資料的載體 稱之為 “json字元串”

json資料存儲采用{}與[]文法

{} => java中的雙列集合 (字典)

[] => java中的單列集合 (數組)

  1. json文法最頂層為 單一{} 或 單一[]
  2. json文法中結構為 {} [] 互相嵌套({}可以嵌套{}[],[]也可以互相嵌套{}[])
  3. json文法中以逗号(,)作為字段分割的辨別(注: 最後一個字段不能添加逗号)
  4. 字典中文法為 {“key”:value}格式 (注: key為字元串)

    多條語句文法:

    {

    “key1”: value1,

    “key2”: value2,

    … : … ,

    “keyn”: valuen

    }

  5. 數組中文法為[value1,value2,value3] 格式(注: value擁有類型)
    1. 數字(整數或浮點數)
    2. 邏輯值(true 或 false)
    3. 字元串(在雙引号中)
    4. 數組(在方括号中)
    5. 函數
    6. 對象(在大括号中)
    7. null
  6. {}和[]中的每一個value均可以為{}|[] ,且多個value類型不一定相同

7.我們在JSON解析中隻有三中情況出現

1.{} 解析’大括号’類型

2. [ ] 解析是’中括号’類型

3. 其實隻有兩種,那第三種則是1與2的組合方法即”{”name”:”小東吖”,”hobby”:[“程式設計”,”電競”,”睡覺”]}”那麼下面分别來看一些這三種類型以及解析

三.解析JSON

SON解析一定要掌握的兩條規則:

1.如果看到是{ }–>使用JSONObject
2.如果看到的[ ]–>使用JSONArray解析
           

掌握了JSON的資料類型和基本文法後,我們對JSON的各種文法類型進行詳細解析(注意掌握兩條規則的使用,掌握了JSON解析就那麼回事)

我們在eclipse裡面操作JSON解析的時候需要第三方jar包的支援 (可以從網上下載下傳)

// JSON字元串以{}包裹,解析為JSONObject對象
        // JSON字元串以[]包裹,解析為JSONArray對象

        // 純數組解析
    public static void main(String[] args) {
        String string = "[\"天津\",\"上海\",\"北京\",\"南京\"]";
        // []是數組 将其解析為JSONArray數組即可 擁有數組的方法
        JSONArray jsonArray = JSON.parseArray(string);
        System.out.println(jsonArray);

        // 純對象解析
        String oString = "{\"name\" : \"小東吖\" }";
        // 大括号是對象類型的 解析為JSONObject類型即可
        JSONObject jsonObject = JSON.parseObject(oString);
        // parseObject的參數(字元串,類名.class); 就可解析為對象
        Student student = jsonObject.parseObject(oString, Student.class);
        System.out.println(student);
           

Student類 通過setter getter 方法去比對屬性

public class Student {
    private String name;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    // toString方法用于控制台輸出  
    @Override
    public String toString() {
        return "Student [name=" + name + "]";
    }
           

三.綜合性解析

  1. 先寫一個JSON檔案
{
    "states":,
    "msg":"藍鷗劍橋學院",
    "data":
    [
            {
                "tag": "Teachers",
                "data": 
                [
                    {
                        "name": "王大錘",
                        "gender": "男",
                        "subject": "尬藝術",
                        "salary": 
                    },
                    {
                        "name": "蒼肖峰",
                        "gender": "女",
                        "subject": "體藝術",
                        "salary": 
                    },
                    {
                        "name": "馬小璐",
                        "gender": "未知",
                        "subject": "媚藝術",
                        "salary": 
                    }
                ]
            },
            {
                "tag": "Students",
                "data": 
                [
                    {
                        "name": "胡一彪",
                        "gender": "男",
                        "age": ,
                        "class": "三班"
                    },
                    {
                        "name": "劉寶寶",
                        "gender": "男",
                        "age": ,
                        "class": "八班"
                    },
                    {
                        "name": "王思思",
                        "gender": "女",
                        "age": ,
                        "class": "四班"
                    },
                    {
                        "name": "雷布斯",
                        "gender": "女",
                        "age": ,
                        "class": "五班"
                    }
                ] 
            }
    ]
}
           
  1. 解析 明确一點解析的結果為對象 需要建立一個School類
  2. 一:第一層 (JSONObject){”status”: “msg”: “data”}

    二:第二層 (JSONArray) []

    三:第三層 (JSONObject) {} 裡面包含”Teachers” “Students” 裡面嵌套的都是(JSONObject){}

    這就需要咱們在解析的時候需要很細緻的去建立對應的屬性值,JSON解析并不難,而難受的地方就提現在對類的建立中,隻要夠細心也超簡單!

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;

import lesson.ls01.JSONs;

// 功能: 對外提供一個公用的JSON解析結果
// 定義單例的原因: 公用--封裝 | 單一 -- 單例
public class AnalyisisJSON {
    // 對外提供單一對象
    private static Map<String,List<Object>> school = null;
    // 對外提供的對象和自身沒關系
    // 不對外提供構造器 且自身構造器不需要做任何操作
    private AnalyisisJSON() {}

    public static Map<String,List<Object>> jsonToMap() {
        // 單例對外提供的單例方法 作為一對象指派
        // 唯一對象為school對應的map 指派的操作為JSON資料的解析
        System.out.println("開始擷取資料!!!");
        if (school == null) {
            school = analyse();
        }
        return school;
    }
    // 解析方法
    public static Map<String,List<Object>> analyse() {
        // 單例 延遲測試單例
        long timeMillis = System.currentTimeMillis();
        while (System.currentTimeMillis()-timeMillis <) {}

        Map<String,List<Object>> map = new HashMap<>();
        String jStr = JSONs.jsonString("src/lesson/ls02/School.json");
        // 第一層
        JSONObject jsonObject = JSON.parseObject(jStr);
        // 第二層
        JSONArray jsonArray = jsonObject.getJSONArray("data");
        // 第三層  分Teachers | Students
        for (int i = ; i < jsonArray.size(); i++) {
            JSONObject jObject = jsonArray.getJSONObject(i);
            // 第四層 Teacher-數組 | Students-數組 
            JSONArray jArray = jObject.getJSONArray("data");

            String tag = jObject.getString("tag");
            // 第五層 整體解析為 List
            if (tag.equals("Teachers")) {
                List<Teacher> ts = JSON.parseArray(jArray.toJSONString(), Teacher.class);
                // 向上轉型 把teacher類轉為object
                List<Object> os = new ArrayList<>(ts);
                map.put(tag, os);
            }
            if (jObject.getString("tag").equals("Students")) {
                List<Student> ss = JSON.parseArray(jArray.toJSONString(), Student.class);
                List<Object> os = new ArrayList<>(ss);
                map.put(tag, os);
            }
        }


        return map;
    }

}
// 這裡我将JSON檔案轉為字元串的方法封裝起來
public class JSONs {
       // 解析JSON檔案轉換成JSON字元串
        // 分析: BufferedReader-行讀取文本内容
        // StringBuffer将讀取的内容一次次拼接
        // 将最終的字元串為結果傳回
    // 功能: 将JSON檔案轉化為JSON字元串,采用 注解 方式解決
    public static String jsonString(String filePath){
        StringBuffer sb = new StringBuffer();
        File file = new File(filePath);
        BufferedReader reader = null;
        try {
            reader = new BufferedReader(new FileReader(file));
            String line = "";
            while ((line = reader.readLine()) != null) { // 讀完是空的
                sb.append(line.trim());
            }

        } catch (Exception e) {
            System.out.println("json字元串解析失敗 -- " + e.getMessage());
        } finally {
                try {
                    if (reader != null)
                    reader.close();
                } catch (IOException e) {
                    System.out.println("流關閉失敗 -- "+ e.getMessage());
                }
        }
        // 構造器将StringBuffer轉為字元串 傳回
        return new String(sb);
    }
}


public class Test {
    public static void main(String[] args) {
        Map<String,List<Object>> school = AnalyisisJSON.jsonToMap();
        System.out.println("school: " + school);
   }
}
           
Student類
import com.alibaba.fastjson.annotation.JSONField;

public class Student {
    private String name;
    private String gender;
    private int age;
    // 注解
    @JSONField(name = "class")
    private String clazz;
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public String getGender() {
        return gender;
    }
    public void setGender(String gender) {
        this.gender = gender;
    }
    public int getAge() {
        return age;
    }
    public void setAge(int age) {
        this.age = age;
    }

    public String getClazz() {
        return clazz;
    }
    public void setClazz(String clazz) {
        this.clazz = clazz;
    }
    @Override
    public String toString() {
        return "Student [name=" + name + ", gender=" + gender + ", age=" + age + ", clazz=" + clazz + "]";
    }

}
Teacher類
public class Teacher {
    private String name;
    private String gender;
    private String subject;
    private String salary;
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public String getGender() {
        return gender;
    }
    public void setGender(String gender) {
        this.gender = gender;
    }
    public String getSubject() {
        return subject;
    }
    public void setSubject(String subject) {
        this.subject = subject;
    }
    public String getSalary() {
        return salary;
    }
    public void setSalary(String salary) {
        this.salary = salary;
    }
    @Override
    public String toString() {
        return "Teacher [name=" + name + ", gender=" + gender + ", subject=" + subject + ", salary=" + salary + "]";
    }
           

其實:

1.首先是對JSON資料的一個分析 先把JSON檔案讀取轉為字元串

2.其次是掌握JSON一些技巧(看到{}對象形JSONObject ,[]數組形JSONArray)

3.而後是對對應的屬性值進行對應的字段封裝建立對應的類(分析要細心,思路要清晰,程式這行需要有耐心不能浮躁)

4.而後是解析中要有明确的思路