JSON详解
关于JSON
JSON是一种数据格式并不是编程语言。JSON是javascript的一个严格子集,利用了javascript的一些模式来表示格式化数据。
并不是只有javascript才能使用JSON,毕竟它只是一种数据格式,很多编程语言都有针对JSON的解析器和序列化器。
JSON语法
JSON可以表示三种类型的值:简单值、数组、对象。
1、简单值:可以在JSON中表示字符串、数字、布尔值、null,但是不支持undefined;
1 console.log(JSON.parse('5')); // 5 2 console.log(JSON.parse(5)); // 5 3 4 console.log(JSON.parse('true')); // true 5 console.log(JSON.parse(true)); // true 6 7 console.log(JSON.parse('"hello"')); // "hello" 8 console.log(JSON.parse("hello")); // 报错 因为hello不是JSON字符串 9 10 console.log(JSON.parse('null')); // null 11 console.log(JSON.parse(null)); // null 12 13 console.log(JSON.parse(undefined)); // 报错 因为JSON不能表示undefined换用null代替
NOTE:
JSON字符串必须用双引号括起来;
在js中表示JSON字符串时最好在外面加上单引号。
2、数组:JSON数组采用的是javascript数组字面量的形式;
1 console.log(JSON.parse('[5,true,"hello",null]')); // [5,true,"hello",null] 2 console.log(JSON.parse('[5,true,"hello",null, undefined]')); // 报错
3、对象:与js对象字面量相比,JSON对象没有变量声明也没有末尾的分号。
console.log(JSON.parse('{"num":5,"stop":true,"str":"hello","empty":null}'));// object{num:5,stop:true,str:"hello",empty: null}
NOTE:JSON的属性必须用双引号
JSON解析和序列化
早期JSON解析基本都使用javascript的eval()函数。但是eval有一些性能和安全上的缺点,ECMAScript对解析JSON对象进行了规范,定义了全局对象JSON,支持的浏览器有标准浏览器和IE8+。对于不支持的浏览器可以引入json2.js文件。
JSON对象有两个方法:stringify()、parse()
1、stringify:将javascript对象序列化为JSON字符串
1 console.log(JSON.stringify(5)); // 5 2 console.log(JSON.stringify(true)); // true 3 console.log(JSON.stringify('hello')); // "hello" 4 console.log(JSON.stringify(null)); // null 5 console.log(JSON.stringify(undefined)); // undefined可以被序列化为undefined后台获取到是undefined字符串 6 //console.log(JSON.parse(JSON.stringify(undefined))); // 出错 7 8 var aArr = [5, true, 'hello', null]; 9 console.log(JSON.stringify(aArr)); //[5,true,"hello",null] 10 var aArr = [5, true, 'hello', null, undefined]; // 数组中的undefined值会被序列化为null而不会跳过 11 console.log(JSON.stringify(aArr)); //[5,true,"hello",null, null] 12 13 var oJson = {num: 5, stop: true, str: 'hello', nu: null}; 14 console.log(JSON.stringify(oJson)); //{"num":5,"stop":true,"str":"hello","nu":null} 15 var oJson = {num: 5, stop: true, str: 'hello', nu: null, un:undefined};// 值为undefined的任何属性都会被跳过 16 console.log(JSON.stringify(oJson)); //{"num":5,"stop":true,"str":"hello","nu":null} 17 var oJson = {num: 5, stop: true, str: 'hello', nu: null, num: 8}; // 同名属性会被后面的覆盖 18 console.log(JSON.stringify(oJson)); //{"num":8,"stop":true,"str":"hello","nu":null} 19 var oJson = {num: 5, stop: true, str: 'hello', nu: null, fn: function(){}}; // 函数属性会被跳过 20 console.log(JSON.stringify(oJson)); //{"num":5,"stop":true,"str":"hello","nu":null} 21 22 23 function Person(age, name){ 24 this.age = age; 25 this.name = name; 26 } 27 var oPerson = new Person(23, 'hum'); 28 console.log(JSON.stringify(oPerson)); //{"age":23,"name":"hum"} 29 Person.prototype.sex = 1; 30 var oPerson = new Person(23, 'hum'); 31 console.log(JSON.stringify(oPerson)); //{"age":23,"name":"hum"} 原型中的属性也不会被序列化
NOTE:
数组中的undefined会被序列化为null
对象中的undefined属性会被跳过
undefined会被序列化为undefined后台能获取到undefined字符串
对象中的函数和原型中的属性都不能被序列化
对象中的同名属性会被后面的覆盖(和js对象一样)
2、parse:将JSON字符串解析会javascript对象(使用参考JSON语法部分)
JSON的两个方法详解
1、stringify
JSON.stringify除了要序列化的对象外,还可以接受两个参数。第一个参数是过滤器,可以是数组,也可以是函数;第二个参数控制JSON字符串中缩进。
过滤器:默认值为null,不会进行任何过滤。
数组过滤器:如果过滤器是数组,那么结果中只包含数组中列出的属性。
1 var oJson = { name: 'hum', age: 20, sex: 1}; 2 console.log(JSON.stringify(oJson, ['age', 'sex'])); // {"age":20,"sex":1}
函数过滤器:如果过滤器是函数,函数可以接受两个参数(属性名和属性值)。结果可以通过函数来修改如果函数返回undefined那么相应的属性会被跳过。
1 var oJson = { name: 'hum', age: 26, sex: 1, love: ['swing', 'jump']}; 2 console.log(JSON.stringify(oJson, function(k, v){ 3 switch (k){ 4 case 'age': 5 return v > 20 ? '成年': '未成年'; 6 case 'love': 7 return v.join(','); 8 case 'sex': 9 return undefined; 10 default : 11 return v; 12 } 13 })); // {"name":"hum","age":"成年","love":"swing,jump"}
JSON字符串缩进:stringify的第三个参数可以是数字,表示每个级别缩进的空格数
1 var oJson = { name: 'hum', age: 26, sex: 1, love: ['swing', 'jump']}; 2 console.log(JSON.stringify(oJson, null, 4)); 3 /* 4 { 5 "name": "hum", 6 "age": 26, 7 "sex": 1, 8 "love": [ 9 "swing", 10 "jump" 11 ] 12 } 13 */
如果第三个参数是字符串,那么这个字符串就是缩进字符(而不是空格)。注意缩进字符串不能超过10个字符否则只会显示前10个字符。
1 var oJson = { name: 'hum', age: 26, sex: 1, love: ['swing', 'jump']}; 2 console.log(JSON.stringify(oJson, null, '--')); 3 /* 4 { 5 --"name": "hum", 6 --"age": 26, 7 --"sex": 1, 8 --"love": [ 9 ----"swing", 10 ----"jump" 11 --] 12 } 13 */
2、parse:parse方法可以接受另一个参数,该参数是函数,该函数可以传递两个参数(属性名和属性值)。如果该函数返回undefined表示要从结果中删除相应的属性,如果返回其他值,将该值插入到结果中。
1 var oJson = { name: 'hum', age: 26, sex: 1, love: ['swing', 'jump'], birthday: '1988-01-12'}; 2 var sJson = JSON.stringify(oJson); 3 console.log(sJson);//{"name":"hum","age":26,"sex":1,"love":["swing","jump"],"birthday":"1988-01-12"} 4 console.log(JSON.parse(sJson)); 5 console.log(JSON.parse(sJson, function (k, v) { 6 if(k == 'birthday'){ // 返回日期对象 7 return new Date(v); 8 }else if(k == 'sex'){ // sex不在了 9 return undefined; 10 }else{ 11 return v; 12 } 13 }));