深刻解析 - JSON对象的点点滴滴

  前言 javascript

    想要比较清楚的研究一个东西,并非说背下它的定义和几个公式就完事了.因此对于JSON的解释我也没有兴趣再COPY一遍它的英文全称和完整命名,你们都知道它是一种数据交换格式,平时也就是看成一种数据类型那么用了,这一点问题都没有,本文只是在了解它的基本概念和前提上稍微深刻一下. java

  正文 web

    1. JSON格式
 跨域

    2001年为了取代繁琐而笨重的XML格式,JSON做为一种轻量级的数据交换格式被提出,做为1999年ECMA-262的一个子集.一经提出JSON就迅速的在Web应用上普及开来,由于相比于XML,JSON书写十分简单方便阅读,同时由于是Javascript的子集因此符合JS的原生语法,能够被解释引擎直接处理.
 数组

    数据格式存在的目的是以必定的形式存储数据,简单说,JSON格式就是一种表示一系列"值"的方法,这些"值"存在于数组或者对象当中.
 服务器

    JSON虽然能够存储值,可是也要遵照必定的规则,固然结构的核心就是"key/vlaue".
 数据结构

    Object - 对象是一个无序的"key/value"集合.
函数


    Array - 数组是值的有序集合.
this


    Value - 值能够是双引号括起来的string,number,true,false,null,object,array,这些结构还能够嵌套使用.
spa


    String - 被双引号包围的任意Unicode字符集合.


    Number - 数值与C和Java的数值很类似.


    看了上面的结构,下面列举一些书写正确和错误的JSON格式:

// 书写正确

["one", "two", "three"]

{ "one": 1, "two": 2, "three": 3 }

{"names": ["张三", "李四"] }

[ { "name": "张三"}, {"name": "李四"} ]

// 书写错误

{ name: "张三", 'age': 32 }  // 属性名必须使用双引号

[32, 64, 128, 0xFFF] // 不能使用十六进制值

{ "name": "张三", age: undefined } // 不能使用undefined

{ "name": "张三",
  "birthday": new Date('Fri, 26 Aug 2011 07:13:10 GMT'),
  "getName": function() {
      return this.name;
  }
} // 不能使用函数和日期对象

    注意空数组和空对象都是符合规范的JSON值,null自己也没有问题.看到这里应该对JSON的格式有所了解了,最起码纠正你们一个误区,JSON不必定非要是{}或者[],而是二者都可. 

    2. JSON对象

    咱们以前提到了JSON诞生于2001年,是ECMA-262的一个子集,后来JSON由于其流行程度以及实用性被加入到ECMA标准中.在ECMA5新增了JSON对象专门用来处理JSON格式,而且附加了stringify()和parse()两个方法.

    平时开发中有时咱们将JSON理解为一个经过大括号和中括号进行结构标记的很长的字符串,这么理解我感受也没错.

    JSON.stringify(o) - 用于将对象转为JSON字符串.    JSON.parse(string) - 用于将JSON字符串转为对象.

    (1) stringify()

JSON.stringify("abc");
// ""abc""

JSON.stringify({ name: "张三" });
// {"name":"张三"}

    这里转为的时候若是遇到一个值是undefined或者是函数,那么该值会被省略,除非这个值是数组的成员,则返回null. 

JSON.stringify({
    f: function() { },
    a: [ function() {}, undefined ]
});
// "{"a":[null,null]}"

    第一个参数是要转换的对象,第二个参数能够没有,也能够是数组参数表示要转化的属性,或者是一个函数用来更改默认的转换.

JSON.stringify({ a:1, b:2 }, ['a']);
// "{"a":1}"

function f(key, value) {
        if (typeof value === "number") {
            value = 2 * value;
        }
        return value;
    }

JSON.stringify({ a:1, b:2 }, f)
// "{"a":2,"b":4}"

    stringify()方法还能够接受第三个参数用来加强返回字符串的可读性,以及更复杂的使用.可是这里不推荐你们这么用,由于使用JSON的目的就是为了简洁明了,若是把数据格式弄得太复杂就失去了自己含义了,因此一般状况下"对象数组"这种复杂度应该足够了.

    (2) parse()

    想要将一个字符串转换为JSON对象,那么传入的字符串必定要是有效的格式,不然程序会出错,为了防止意外能够将这个过程放到try/catch代码块中.

JSON.parse('{}'); // {}
JSON.parse('true'); // true
JSON.parse('"foo"'); // "foo"
JSON.parse('[1, 5, "false"]'); // [1, 5, "false"]
JSON.parse('null'); // null

var o = JSON.parse('{"name":"张三"}');

o.name
// 张三

    它也能够接受一个第二参数,经过一个函数改变默认转换的行为.

function f(key, value) {

  if ( key === ""){
      return value;
  }
    
  if ( key === "a" ) {
    return value + 10;
  }
}

var o = JSON.parse('{"a":1,"b":2}', f);

o.a
// 11

o.b
// undefined

    3. 误区

    很是多的人在使用了好久的JSON后都没有弄明白什么是JSON,虽然上面未来字符串和JSON对象的转换.可是我依然要纠正,javascript中没有一种数据类型叫作"JSON对象".能够说JSON对象是在一种特殊环境上下文中产生的叫法,JSON在平常的表现形式更多的是一个拥有复杂数据结构的字符串,只是能够被转换为对象.

// 这是JSON字符串
var foo = '{ "prop": "val" }';
 
// 这是对象字面量
var bar = { "prop": "val" };

    4. 一点点扩展 - JSONP    

    说到这里JSON就没什么东西了,做为一种数据格式在外面平常使用的范畴它的深度也差很少就是这些了.写着JSON到最后想起来了JSONP,因此顺带着也把它带出来.

    看名字就会以为JSON和JSONP有那么点好基友的味道,根据百度百科对JSONP的解释是:JSON with Padding的略称,一个非官方协议,容许在服务器集成Script tags返回给客户端,经过JS callback的形式实现跨域访问.

    说到跨域我象看过的人应该对JSONP有一点印象,比较经典的说跨域的文章几乎都提到了一种解决方案就是JSONP.这里我不想解释跨域的相关问题,因此我就针对JSONP解读一下:

    Ajax在请求文件时只要是跨域请求一律不许,可是Web页面上调用JS文件则不受跨域的限制,因而咱们就想出一种方案,把服务器上的数据设法装进JS格式的文件里,而后让客户端调用.这时咱们想到JSON被JS原生支持并且能够存储复杂数据,这下好了,web端经过与调用脚本同样的方式,调用跨域服务器上动态生成的js格式文件,客户端在对这种JSON文件调用成功后就能够随便使用了.为了方便客户端使用数据,逐渐造成一种非正式的传输协议,被称为JSONP,它规定容许用户传递一个callback参数给服务端,而后服务器返回数据时会将这个callback参数做为函数名来包裹JSON数据.

    结尾

    关于JSON和相关的东西就写了这些,参考了网上一些资料和本身的使用心得,水平有限,有不足的地方还请谅解,欢迎留言给我.

相关文章
相关标签/搜索