伊莉討論區
標題:
JavaScript 輕量資料格式 JSON
[打印本頁]
作者:
isve
時間:
2016-10-25 12:07 AM
標題:
JavaScript 輕量資料格式 JSON
JSON 全名 JavaScript Object Notation,為 JavaScript 物件實字(Object literal)的子集,你可以在 Introducing JSON 找到詳細的 JSON 格式說明。大致而言,與物件實字格式類似,主要注意的是JSON:
•名稱為字串,必須用 "" 雙引號包括
•值可以是"雙引號包括的字串,或者是數字、true、false、null、物件或陣列。
•不支援 JavaScript 的 Date、Error、規則表示式或函式表示。
舉個例子來說,下面是個物件實字:
var obj = {
name : 'Justin',
age : 35,
childs : [ {name : 'hamimi', age : 3} ]
};
若使用JSON表示,則是如下:
var json = '{"name":"Justin","age":35,"childs":[{"name":"hamimi","age":3}]}';
若為排版會比較容易觀察:
{
"name":"Justin",
"age":35,
"childs":[
{
"name":"hamimi",
"age":3
}
]
}
JSON.stringify
ECMAScript 5 規範中,如果要從物件建立 JSON 字串,只要使用 JSON.stringify。例如:
var obj = {
name : 'Justin',
age : 35,
childs : [ {name : 'hamimi', age : 3} ]
};
var json = JSON.stringify(obj);
// {"name":"Justin","age":35,"childs":[{"name":"hamimi","age":3}]}
console.log(json);
//{"name":"Justin","age":35}
console.log(JSON.stringify(obj, ['name', 'age']));
JSON.stringify 可以指定第二個引數,若指定陣列,只會針對該陣列轉換 JSON 字串,若指定函式,這個函式可接受物件的特性與值,可以自行決定如何轉換為 JSON 字串。
第一次呼叫指定函式時,鍵為空字串,而值為要被轉換的物件本身,之後逐一以每個特性與值來呼叫函式,傳回值若是數字、字串、布林值,就會被加入 JSON 字串,如果傳回物件,則會遞迴地呼叫指定的函式進行轉換,如果傳回 undefined,該特性就不會被加入 JSON 字串。
例如,上頭的 obj 轉換為 JSON 字串時,不想要有 age 特性的話,可以如下:
var obj = {
name : 'Justin',
age : 35,
childs : [ {name : 'hamimi', age : 3} ]
};
console.log(JSON.stringify(obj, function(key, value) {
if(key === 'age'){
return undefined;
}
return value;
}));
JSON.stringify 可以指定第三個引數,如果是 1 到 10 的數字,會自動換行並以指定數字作為縮排層次,如果指定字元,就會以指定的字元來進行縮排。例如:
var obj = {
name : 'Justin',
age : 35,
childs : [ {name : 'hamimi', age : 3} ]
};
function replacer(key, value) {
return key === 'age' ? undefined : value;
}
console.log(JSON.stringify(obj, replacer, 2));
顯示的結果會是兩個空格縮排:
{
"name": "Justin",
"childs": [
{
"name": "hamimi"
}
]
}
如果物件本身定義有 toJSON 方法,JSON.stringify 會使用 toJSON 傳回的物件來進行 JSON 字串轉換。例如:
var obj = {
name : 'Justin',
age : 35,
toJSON : function() {
return {
name : this.name.toUpperCase(),
age : this.age
};
}
};
// {"name":"JUSTIN","age":35}
console.log(JSON.stringify(obj));
JSON.parse
如果想將 JSON 字串剖析為 JavaScript 物件,可以使用 JSON.parse,例如:
var json = '{"name":"Justin","age":35,"childs":[{"name":"hamimi","age":3}]}';
var obj = JSON.parse(json);
console.log(obj.name); // Justin
每個鍵值被剖析為值之後,可以指定一個函式來決定被剖析後的值如何轉換,傳回的值決定了最後得到的物件上之特性值,如果傳回 undefined,就不會包括該特性。例如:
var json = '{"name":"Justin","age":35,"childs":[{"name":"hamimi","age":3}]}';
var obj = JSON.parse(json, function(key, value) {
if(key === 'age'){
return undefined;
}
return value;
});
console.log(obj); // { name: 'Justin', childs: [ { name: 'hamimi' } ] }
如果是沒有內建 JSON 支援的平台(像是一些舊瀏覽器),可以在 Introducing JSON 下載 json2.js,用以獲得上述的相關 JSON 方法。
作者:
jehovahcloud
時間:
2017-2-15 08:48 PM
分享一個 JSON 在 PHP 裡處理時容易中招的點,主要是因為 php 太神了,所以才會出現這東西...
php 將 array 轉成 json 基本上會照下面法則走。
1. json_encode([ 'prop1' => 1, 'prop2' => 2]) 會輸出 { "prop1":1, "prop2":2 }
2. json_encode([]) 還是會輸出 []
因為 php 的 array 很方便,有時候大家會習慣用 array 來操作,這種時候就很容易因為輸入跟輸出的轉換會造成錯誤。舉例來說,如果傳入的資料是下面的資料
$input = '{ "a":1, "b":2, "c":{ "invalid":"str" } }';
我們有時候會習慣用下面的方法來將資料解析成 php array。
$data = json_decode( $input, true );
然後我們把不要的資料過濾掉
unset($data["c"]["invalid"]);
接著一般來說會用下面方式把資料轉回 json 要送回去給 js。
$output = json_encode($data);
這個時候 js 可能就爆開了!!!因為... $output 裡面會變成下面的 JSON 格式。
$output = '{ "a":1, "b":2, "c":[] }'
本來放物件的地方變成放 array...
這東西的解決方法要就在輸出時多加 if 來檢查,不然就是在 json_decode 時不要強制把 object 轉乘 assoc array,也就是 json_decode 第二個參數保持預設的 false。
然後在程式碼中不要偷懶,已經知道是 object 就保持 object,array 的就確保他是 array。
作者:
jehovahcloud
時間:
2017-2-15 08:53 PM
另外再講一個也很容易中招的東西...
拿下面資料舉例:
$data = [ "item1", "item2", "item3" ];
一般來說,json_encode($data) 時會是很正常的下面的值
[ "item1", "item2", "item3" ]
但是如果在操作時,我們偶而會把某個項目用下面的方法拿掉拿掉。
unset($data[1]);
這個時候就很神奇了...
json_encode($data) 會輸出 { "0":"item1", "3":"item3" }
因為 php 存 array 的方式的問題會造成 json_encode 在判斷 array 時出問題...
所以這種狀況要用下面的方式處理。
json_encode(array_values($data))
php 才會確保輸出 [ "item1", "item3" ]
不然你在 js 以為是 array 的被強制變成 object...
這樣 js 那邊就超級容易爆炸的,而且很可悲的是...這種 bug 通常要找很久....
歡迎光臨 伊莉討論區 (http://www1.eyny.com/)
Powered by Discuz!