JSON:JavaScript物件表示法
1.1 JSON說明
曾經一段時間,XML是網際網路傳遞資料的統一標準,但是業界一直不乏質疑XML的人士,他們都認為XML過於繁瑣,冗長;提取資料也過於麻煩
2006年,JSON被提交給了IETF;在這之後,JSON逐漸發展起來,在網際網路上得到廣泛應用;
我們要記住:JSON只是一種資料格式,主要用來傳遞資料,並不是一種程式語言,雖然與JavaScript的語法相似,但是並不是JavaScript才使用JSON,畢竟JSON只是一種資料格式,很多程式語言都有針對JSON的解析器和序列化器
1.2 JSON語法
(1)基礎語法:
- 將JavaScript資料轉化為JSON資料,也叫——序列化
// 把JavaScript物件序列化成JSON字串
var jsonText = JSON.stringify(book);
- 將JSON資料轉化為JavaScript資料,也叫——解析
// 將JSON物件解析成原生JavaScript值
var js = JSON.parse(jsonText);
(2)JSON可以表示以下三種型別的資料:
簡單值:可以在JSON裡面表示 數值、字串、布林值、null;不支援 undefined
物件:複雜資料型別,儲存一組鍵值對;在JSON裡,物件的鍵一定要加雙引號,值可以是簡單值,也可以是複雜資料型別的值
陣列:複雜資料型別,儲存一組值;值可以是簡單值,也可以是複雜資料型別的值
JSON不支援變數,函式,物件例項等,它只是一種表示資料的格式,裡面只用來儲存資料,不會有邏輯、操作等程式碼在裡面
-
簡單值,簡單值中的字串必須使用雙引號,使用單引號報錯
number、string、bool、null
-
物件,直接使用{ }符號,沒有變數,括號後面不用加分號;同一個物件中不應該有相同的屬性,以下兩個location屬性,分別屬於不同物件,這樣是沒有問題的;
{ "name": "過青年", "age": 20, "arr": [1,2,3,4], "location": "江西宜春", "school": { "location": "江西南昌" } }
-
陣列,直接使用[ ]符號,裡面簡單值和複雜資料型別可以組合使用,構成更復雜的資料集合;
[ 20, { "name": "過青年", "age": 20 }, [1,2,3], "過青年" ]
物件和陣列一般是JSON資料最外層的結構,利用它們可以創造出各種各樣的資料集合
1.3 序列化和解析
1.31 序列化選項
(1)過濾結果
JSON.stringify(js物件,過濾器引數)
方法可以傳遞兩個引數
-
如果過濾器引數是陣列,那麼JSON.stringify( )的結果將只包含陣列中列出的屬性
var obj = { name: "過青年", age: 20, arr: [1,2,3,4], location: "江西宜春", school: { location: "江西南昌" } } console.log(JSON.stringify(obj,["name","age","arr"])); // {"name":"過青年","age":20,"arr":[1,2,3,4]}
-
如果過濾器引數是函式(過濾函式),可以改變序列化物件的結果;函式第一個引數預設是屬性名(鍵),第二個引數預設是屬性值
如果返回的是
undefined
,則相應的屬性名和屬性值會被忽略
var jsonText = JSON.stringify(obj,function(key,value){
switch (key) {
case "name":
return 20;
case "age":
return "過青年";
case "arr":
return [4,3,2,1];
case "school":
return undefined;
default:
return value;
}
});
console.log(jsonText);
// {"name":20,"age":"過青年","arr":[4,3,2,1],"location":"江西宜春"}
(2)格式化:字串縮排、空白符
第三個引數控制縮排和空白符;
- 如果是一個數值,表示空白字元個數,最大為10,大於10的轉換成10;如果第三個引數是有效引數,會自動幫我們插入換行符,提高可讀性;
var jsonText = JSON.stringify(obj,null,4);
console.log(jsonText);
/*
{
"name": "過青年",
"age": 20,
"arr": [
1,
2,
3,
4
],
"location": "江西宜春",
"school": {
"location": "江西南昌"
}
}
*/
- 如果是一個字串,這個字串將被作為縮排字元,而非原來的空白字元作為縮排;字串引數裡的字元個數不能超過10個,超過10個,結果中只出現前十個字元;
var jsonText = JSON.stringify(obj,null,"-");
console.log(jsonText);
/*
{
-"name": "過青年",
-"age": 20,
-"arr": [
--1,
--2,
--3,
--4
-],
-"location": "江西宜春",
-"school": {
--"location": "江西南昌"
-}
}
*/
(3)toJSON
方法
我們可以在需要序列化的物件上增加一個toJSON
方法,這樣當使用JSON.stringify()方法時,實際上就是呼叫了物件中的toJSON()方法
var obj = {
name: "過青年",
age: 20,
arr: [1,2,3,4],
location: "江西宜春",
school: {
location: "江西南昌"
},
toJSON:function(){
return this.name;
}
}
var jsonText = JSON.stringify(obj);
console.log(jsonText);
// 過青年
(4)把一個物件傳入JSON.stringify()中,序列化該物件的順序如下:
<1> 如果該物件中有toJSON方法,則直接呼叫該方法;
<2> 如果JSON.stringify()中有第二個引數,則應用過濾器,過濾器接受的值就是<1>中返回的值
<3> 過濾器處理<1>中返回的值
<4> 如果有第三個引數,執行相應的格式化
var obj = {
name: "過青年",
age: 20,
arr: [1,2,3,4],
location: "江西宜春",
school: {
"location": "江西南昌"
},
toJSON:function(){
name = this.name;
age = this.age;
return {name,age};
}
}
var jsonText = JSON.stringify(obj,function(key,value){
if(key === "name") {
return "哈哈哈";
}else{
return value;
}
});
console.log(jsonText); // {"name":"哈哈哈","age":20}
理解序列化物件的過程還是很重要的
1.31 解析選項
JSON.parse()方法也有兩個引數,第二個引數是一個函式,叫做還原函式
var obj = {
name: "過青年",
age: 20,
arr: [1,2,3,4],
location: "江西宜春",
school: {
"location": "江西南昌"
}
};
var jsonText = JSON.stringify(obj);
var jsText = JSON.parse(jsonText,function(key,value){
if (key === "name") {
return "哈哈哈哈";
} else {
return value;
}
});
console.log(jsText);
//{name: '哈哈哈哈', age: 20, arr: Array(4), location: '江西宜春', school: {…}}
1.4 總結
JSON.stringify()
用於序列化,JSON.parse()
用於解析JSON.stringify()
有三個引數,第一個是js物件,第二個是過濾器,第三個是用來格式化JSON輸出JSON.parse()
有兩個引數,第一個引數是JSON物件,第二個引數是還原函式- js物件中可以宣告一個
toJSON
方法,當JSON.stringify()
方法呼叫時,自動執行toJSON
方法 - 注意,
JSON.stringify()
方法的返回值都是字串型別