因此,JSON.stringify提供了一种转换JS对象的好方法:
var baz = {"foo":1, "bar":someFunction};
输入JSON字符串,例如:
{"foo":1}
它使用一个可选的第二个参数来执行此操作,该参数控制应序列化哪些字段:
JSON.stringify(baz, ["foo"]);
很好,但是有一个问题。假设您的“ baz”实际上是另一个对象的属性,并且您想要序列化另一个对象:
someObject.baz = {"foo":1, "bar":someFunction}; JSON.stringify(someObject, ["baz"]);
好吧,通常您只需要在baz上定义一个toJSON方法,例如:
someObject.baz = {"foo":1, "bar":someFunction}; someObject.baz.toJSON = function() { /* logic to "toJSON" baz*/ } JSON.stringify(someObject, ["baz"]);
现在,正如我前面提到的,我们已经有了完美的逻辑来“ toJSON” baz:
someObject.baz.toJSON = function() { return JSON.stringify(baz, ["foo"]); }
但是,如果您尝试将其放入toJSON中,则会遇到递归错误,因为stringify将触发toJSON,后者将触发stringify,这将… :-(
您可以通过以下方法解决此问题:
someObject.baz.toJSON = function() { var oldToJON = this.toJSON; this.toJSON = null; var ret = JSON.stringify(baz, ["foo"]); this.toJSON = oldToJON; return ret; }
但是…这似乎是错误的。所以,我的问题是:有什么方法可以利用对象的toJSON方法 内部 的JSON.stringify内置的强大序列化功能(而在stringify操作期间不必隐藏toJSON方法本身)?
克罗克福德的json2.js说:
toJSON方法不序列化:它返回应序列化的名称/值对表示的值,如果不应该序列化则返回undefined。
因此,仅希望您返回要序列化的值。在您的情况下,baz.toJSON应仅返回baz要序列化的对象部分:
baz.toJSON
baz
someObject.baz.toJSON = function() { return { foo: this.foo }; };