JSON是什么

/

提起 JSON,作为如今最受欢迎的数据交换格式,可以说是无人不知、无人不晓了。

JSON 全称 JavaScript Object Notation( JS 对象简谱),自诞生之初的小目标就是为了取代XML的江湖地位,短短几年,凭借其简洁易用的特性,早就实现了当初的小目标。最近微信支付的数据格式从最初的 XML 更新为 JSON 也算是迷途知返了。

因为 JavaScript 语言本身具有很明显 C语言风格,导致 JSON 也保持了 C系语言的习惯,熟悉 C语言、Java、Python 等语言的开发人员可以很容易的接受 JSON。

JSON 的核心思想之一就是“轻量化”,但是 “keep it simple” 说起容易,做起来难。今天就仔细研究一下 JSON 的标准到底怎样简洁,看看其广受欢迎的背后原因。

0. 概述

JSON 定义了6种数据类型,分别是 null、boolean(包括true,false)、number、string、array 以及 object。其中前四个是基本类型,后两个为数据集合。

下面就借助编译里面经常用到的有穷状态机,详细的介绍一下 JSON 的数据类型。

1. null、true 和 false

null 是 JS 中一个特殊的空对象,而且也很容易映射到其他语言,比如Python中的None。

boolean类型的两个值 true 和 false,同 null 一样,也很直观。

null、true、false,这三个类型的状态机相对简单,都是按照字母拼写的直线。

2. number

number的状态机就比较复杂了

本来 JavaScript 里面表示数值只有 number 一种类型,没有区分 int 跟 float ,JSON 更进一步,规定其中的数值只能是十进制数,其形式包含可选的负号、整数部分、可选的小数部分、可选的指数部分

因为number的状态机比较复杂,这里给出对应的正则表达式,可以跟状态机一起加深理解:

  1. -?([0]|([1-9]\d*))(\.\d*)?([eE][-+]?\d*)?

3. String

相较于 JS 宽松的语言规范,JSON 对 string 做出了更严格的限制,要求其只能被双引号(“)包裹。但是相较于 C语言需要严格区分字符和字符串,JSON 又显得宽松许多,双引号包裹的零个或者一个字符都是正确的 string。特殊字符可以使用反斜线(\)进行转义,比如换行符(\n)。

需要注意的是关于 Unicode 的表示,由于 Unicode 的码点范围为 0 至 0x10FFFF,对于超过 0xFFFF 的码点在 JSON 里需要高低位两组 “\uXXXX” 来表示:如果第一个码点是 0xD800 至 0xDBFF,我们便知道它的代码对的高代理项(high surrogate),之后应该伴随一个 0xDC00 至0xDFFF 的低代理项(low surrogate)。其转换规则如下:

  1. codepoint = 0x10000 + (高位 0xD800) × 0x400 + (低位 0xDC00)

4. array

array 是值的有序集合,其中值可以为任何合法的 JSON 类型。一个 array 以左中括号([)开始, 右中括号(])结束。多个值之间使用 逗号(,) 分隔。

array 在许多语言中都有含义相似的集合形式,比如 Java 的 List 。

5. obj**ect**

object,即对象,是一个无序的“‘键/值’对”集合。一个对象以左大括号( {) 开始, 右大括号(}) 结束。“键”跟“值”之间使用冒号 (:)分割,多个“‘键/值’对”之间使用逗号( ,) 分隔。

JSON 的对象就是哈希表,在很多编程语言里面都有对应的内置结构,只不过是 JSON 要求 key 必须为字符串。

6. 总结

一个合法的JSON串为可选的空白符包裹任意值类型。其中空白符的范围限定于:空格、换行(\n)、回车(\r)和制表符(\t)。集合类型的值之间是可以任意嵌套的。

了解了标准规范会发现 JSON 真的确实简单,不过话又说回来,我们也要了解 JSON 也并非完美无缺的,举个例子:因为 JSON 只有词法特性,没有语法特性,所以通信双方的协商就显得特别关键。

Reproduced please indicate the author and the source, and error a link to this page.
text link: //v2ci.com/29.html