0. 背景
XML曾是web结构化数据传输的事实标准,然而业界一直不乏质疑XML的声音,也发展出了一些替代方案,JSON就是最流行的一种。
JSON(JavaScript Object Notation,JavaScript对象表示法)是JavaScript语言的严格子集,通过JavaScript的模式来结构化表示数据。JSON拥有类似XML的特点:纯文本、自我描述性、层级结构等。并不是只有JavaScript可以使用JSON,作为一种广泛使用的数据格式,绝大多数语言已经支持JSON的解析和序列化。
1. 基本语法
- 基本类型:数值、布尔值、字符串、null
- 对象:一组有序键值对。每个键值对的值又可以是任意类型
- 数组:一组有序值的列表,可按数值索引访问。每个值都可以是任意类型
1.1 基本类型
1.2 对象
{
"name": "Morty",
"age": 14
}
{
"name": "Morty",
"age": 14,
"grandpa": {
"name": "Rick",
"age": 70
}
}
1.3 数组
{
"name": "Morty",
"age": 14,
"grandpa": {
"name": "Rick",
"age": 70
},
"parent": [
{"name": "Jerry", "age": 35},
{"name": "Beth", "age": 35}
]
}
2. 解析和序列化
2.1 JSON对象
- stringify(),将JavaScript对象序列化为JSON字符串
- parse(),和将JSON字符串解析为JavaScript对象。
var computer = {
CPU: "i7 8700K",
GPU: "GTX 1080Ti",
RAM: "16G DDR4",
DISK: ["256G SSD", "2T HDD"],
};
var jsonTest = JSON.stringify(computer); //序列化
var computerCopy = JSON.parse(jsonTest); //解析
默认情况下,stringify()输出的JSON字符串中不会包含任何空白字符,上例中jsonTest如下:2.2 序列化
- 第一个参数:过滤器,一个数组或函数
- 第二个参数:选项,选择JSON字符串是否缩进
2.2.1 过滤器
var jsonTest = JSON.stringify(computer, ["CPU", "GPU"]);
jsonTest如下:var jsonTest = JSON.stringify(computer, function(key, value) {
switch(key) {
case "CPU":
return undefined;
case "RAM":
return 16;
case "DISK":
return value.join("500G SSHD");
default:
return value;
}
});
var computerCopy = JSON.parse(jsonTest);
此时jsonTest如下:- 根据属性名找到要处理的对象属性
- 函数返回值就是处理后的属性值(若返回undefined则该属性会略过)
2.2.2 缩进控制
var jsonTest = JSON.stringify(computer, null, 4);
此时jsonTest如下:"CPU": "i7 8700K",
"GPU": "GTX 1080Ti",
"RAM": "16G DDR4",
"DISK": [
"256G SSD",
"2T HDD"
]
}
例如传入字符串"--":
--"CPU": "i7 8700K",
--"GPU": "GTX 1080Ti",
--"RAM": "16G DDR4",
--"DISK": [
----"256G SSD",
----"2T HDD"
--]
}
2.2.3 toJSON()
var computer = {
CPU: "i7 8700K",
GPU: "GTX 1080Ti",
RAM: "16G DDR4",
DISK: ["256G SSD", "2T HDD"],
toJSON: function() {
return this.CPU + ", " + this.GPU;
}
};
var jsonTest = JSON.stringify(computer);
此时jsonText为:2.3 解析
JSON.parse()也可以接受另一个参数:一个函数,也是作用于每个键值对。为了区分JSON.stringify()上的替换函数(replacer),这个函数被称为还原函数(reviver),实际上两个函数的参数是相同的:都是一对键值对。var computer = {
CPU: "i7 8700K",
GPU: "GTX 1080Ti",
RAM: "16G DDR4",
DISK: ["256G SSD", "2T HDD"],
releaseDate: new Date(2017, 11, 11)
};
var jsonTest = JSON.stringify(computer);
var computerCopy = JSON.parse(jsonTest, function(key, value) {
if (key === "releaseDate") {
return new Date(value);
} else {
return value;
}
});
console.log(computerCopy.releaseDate.getFullYear());
上例computer对象的属性releaseDate中保存着一个Date对象。序列化后的jsonTest中保存着一个Date值,若不在parse()中将其转化为一个Date对象,就无法调用getFullYear()方法。