这个问题是我上一期提问的后续问题:JavaScript Serialization and Methods。虽然相关,我相信这是不同的,这就是我开始这个线程的原因。无论...
我有一个复杂的对象树,我需要在页面之间传递。因此,我正在尝试序列化和反序列化我的对象。特别是我的一个对象有几个子对象集合。这些子对象类型中的每一个都有一个函数,我正在尝试调用它。不幸的是,我没有运气。我设置了一个测试项目,试图找出问题并找到问题的根源。目前,我在一个名为objects.js的单独文件中定义了我的JavaScript对象。那个文件看起来像这样:
objects.js
function MyChild() { this.init(); }
MyChild.prototype = {
data: {
id: 0,
fullName: "",
},
init: function () {
},
save: function (key) {
},
load: function (key) {
},
test: function () {
alert("Testing Child functions");
}
}
function MyParent() { this.init(); }
MyParent.prototype = {
data: {
id: "",
children: null
},
init: function () {
this.data.children = [];
},
save: function (key) {
window.localStorage.setItem(key, JSON.stringify(this.data));
},
load: function (key) {
var temp = window.localStorage.getItem(key);
if (temp != null) {
this.data = JSON.parse(temp);
$.each(this.data.children, function (i, r) {
});
}
},
test: function () {
alert("Testing Parent functions");
}
}
我正在创建,序列化,反序列化以及尝试与.html文件中的这些对象进行交互。这个.html文件显示在这里:
的test.html
<div>
<input id="button1" type="button" value="Create Object Tree" onclick="button1Click();" /><br />
<input id="button2" type="button" value="Retrieve and Execute" onclick="button2Click();" /><br />
</div>
<script type="text/javascript">
function button1Click() {
var child = new MyChild();
child.data.id = 1;
var p = new MyParent();
p.data.id = "A";
p.data.children.push(child);
p.save("A");
}
function button2Click() {
var storedParent = new MyParent();
storedParent.load("A");
storedParent.test(); // This works
alert(storedParent.data.children.length); // This displays "1" like I would expect
alert(storedParent.data.children[0].data.id); // This does NOT work.
storedParent.data.children[0].test(); // This does NOT work.
}
</script>
我不确定我做错了什么。有人可以帮我理解这个吗?可以somone请帮我修复我的例子。我有一种预感,我没有正确地序列化MyChild对象。但我不明白我应该如何序列化/反序列化它们与MyParent。
谢谢!
答案 0 :(得分:2)
您需要将data
存储在每个对象中,而不是prototype
内。
存储在对象prototype
中的数据在所有实例之间共享,不会被JSON.stringify
序列化,因此您的对象数据永远不会在本地存储中结束。
要修复此问题,请在this
函数中向this.init()
添加数据:
MyChild.prototype = {
init: function() {
this.data = {
id: 0,
fullName: ""
};
},
...
}
MyParent.prototype = {
init: function() {
this.data = {
id: "",
children: []
}
},
...
}
http://jsfiddle.net/alnitak/fdwVB/
的工作样本请注意,将MyChild
中的函数附加到检索到的数据非常棘手。以下代码似乎有效:
load: function(key) {
var temp = window.localStorage.getItem(key);
if (temp != null) {
this.data = JSON.parse(temp);
var children = this.data.children;
for (var i = 0; i < children.length; ++i) {
children[i] = $.extend(new MyChild(), children[i]);
}
}
},
但请注意,它的工作原理是为每个检索到的条目构建一个新的“默认”子级,然后用序列化的值覆盖该子级的数据。
如果构造函数具有“副作用”,则可能会出现问题。
更好的方法可能是允许MyChild()
构造函数使用可选的初始值对象而不是默认值。