JSON已经逐渐替代XML被全世界的开发者广泛使用。本文深入讲解JavaScript中使用JSON.stringify的一些细节问题。首先简单回顾一下JSON和JavaScript:
-
<李>不是所有的合法的JSON都是有效的JavaScript,李>
<李> JSON只是一个文本格式;李>
<李> JSON中的数字是十进制。李>
让foo={2, b:函数(){}}; JSON.stringify (foo);//皗“a”: 2}”
JSON.stringify函数将一个JavaScript对象转换成文本化的JSON。不能被文本化的属性会被忽略. foo中属性b的值是函数定义,没有被转换而丢失。
还有哪些属性也不能转换?
<强> 1。循环引用强>
如果一个对象的属性值通过某种间接的方式指回该对象本身,那么就是一个循环引用。比如:
={var酒吧 答:{ c: foo } }; var foo={ b:酒吧};
属性c指向自己,如果层层解析,将会进入一个无限循环。我们尝试将其打印出来看看:
让fooStringified=JSON.stringify (foo); console.log (fooStringified);//{" b ": {" a ": {}}}
c的属性指向foo对象,foo对象中b的属性又指向酒吧对象而无法处理,整个被忽略而返回空对象。
如下定义(原文中的例子)是无法通过编译的:
让foo={b: foo};
错误信息:
ReferenceError: foo不是定义 在repl:一14
在函数式语言Haskell中,因为有懒惰的评价技术,可以使用类似的定义方法。
让foo={b:未定义的}; JSON.stringify (foo);//{}//符号 foo。b=符号(); JSON.stringify (foo);//{}
例外情况
在数组中,不可函数被把的元素用空填充。
让foo=[符号()、定义、功能(){},“作品”) JSON.stringify (foo);//翱?空,空,'工作']”
这样可以保持数组本身的“形状”,也就是每一个元素原本的索引。
<强>为什么有些属性无法函数被把呢? 强>
因为JSON是一个通用的文本格式,和语言无关。设想如果将函数定义函数也把的话,如何判断是哪种语言,并且通过合适的方式将其呈现出来将会变得特别复杂。特别是和语言相关的一些特性,比如JavaScript中的象征。
ECMASCript官方也特意强调了这一点:
它不试图强加ECMAScript的内部数据表示> 函数的人(第一,去年){ 这一点。firstName=第一; 这一点。去年=去年; } Person.prototype。过程=function () { 返回。firstName +的+ this.lastName; }; 让正面=new人(“正面”,“P”); JSON.stringify(正面);//皗“firstName”:“正面”、“最后”:“P”}”
人实例正面的进程函数没有函数被把假。想如果服务器只想要正面的全称,而不是分别获取姓和名,我们可以直接定义toJSON来达到目的:
Person.prototype。toJSON函数=(){ 返回{fullName: this.process ();}; }; 让正面=new人(“正面”,“P”); JSON.stringify(正面);//皗”fullName”:“正面P "} "
定义toJSON的优点是复用性和稳定的性,你可以将正面配合任何库使用,传输的数据都将是你通过toJSON定义而返回的fullName。
//jQuery 美元。邮报》(“端点”,正面);//角2 this.httpService。邮报》(“端点”,正面)
JSON.stringify完整的定义如下:
JSON。stringify(价值、替代者# 63;空间# 63;)
代用品和空间都是可选参数,接下来我们来分别讲解。
<强>代用品强>
代用品是一个过滤函数或则一个数组包含要函数被把的属性名。如果没有定义,默认所有属性都函数被把。
<强> 1。数组强>
只有在数组中的属性函数被把:
让foo={ 答:1, 乙:“字符串”, c:假 }; JSON。stringify (foo [a, b]);//皗””:1、“b”:“字符串”}”
嵌套属性也同样会被过滤: