如何在JavaScript中序列化对象?

时间:2012-08-01 13:04:19

标签: javascript node.js

例如我有课程:

function Test() {
}

Test.prototype = {
    'setTest' : function(test) {
        this.test = test;
    }
}
var test = new Test();
Test.setTest('test');

我想在数据库中保存对象测试。 如何将对象测试序列化为字符串? (方法,变量等)

6 个答案:

答案 0 :(得分:11)

简单用json

JSON.stringify( test );

答案 1 :(得分:8)

在这种情况下,对于你问的问题,实际上没有办法做你想做的事。您的请求的问题在于“序列化附加到对象的所有内容,包括函数”。

序列化通常仅针对数据发生,因为可执行文件通常是机器绑定的,因为它们是基于某些特征针对给定机器编译的。现在,有理由说javascript函数只需要一个javascript解释器,因为javascript是一次性写入,无处不在。但是当人们编写序列化程序时,因为所有序列化程序的工作方式都相同,所以我们只为数据编写它们。在这种情况下,行业标准是JSON,它是一个仅限对象数据的序列化器。

此时有三种解决方案可供您使用:

  1. 编写自己的封装函数的serialier / deserializer。这可能很棘手,因为并非所有的javascript引擎都能让您访问源代码。
  2. 编写自己的重新加载机制,在每次还原时生成特定的新初始化类型,并将类型名称保存为序列化中的一个属性。这样,每个变量的初始化为您提供了方法,然后与数据合并为您提供了完整的对象。
  3. 将每个函数存储为字符串,并根据需要随时进行评估。这非常棘手,很容易出错。我认为这不会有任何帮助,因为它非常脆弱。但是,它是一种选择,不容忽视。
  4. 我知道3是1的子答案,所以你可以认为它只有两个有用的答案。

    我知道这表面上适用于Chrome和IE9,所以它应该适用于大多数用户可能会使用它的地方:

    var abc = function(thing) { return thing; }
    abc.toString();
    // gives "function(thing) { return thing; }" on the command line
    

    所以你当然可以将方法序列化为字符串来代替实际的方法,但是你需要创建一个重复的对象,这样你就可以捕获源对象上的每个元素(我想,而不是替换它们)位)。

    希望这可以帮助你更多地思考这个问题,并且可能意识到你不需要序列化这些方法(没有人知道,不合理)。

答案 2 :(得分:3)

执行此操作的最佳方法是编写自己的serialize方法,该方法基于getter创建具有属性的JSON对象。通常,您为每个属性定义一个getter。因此它适用于大多数情况(因此您不必为每个类定义序列化方法)。

function serialize(obj) {
   var serialized = {};

   for(var prop in obj) {
        if (obj.hasOwnProperty(prop) && typeof obj[prop] == 'function') {
           if (/^get.*/.test(prop)) {
               var value = obj[prop]();
               var name = prop.replace('get', '');

               if (typeof value === 'object') {
                   serialized[name] = this.serialize(value);
                   continue;
               }

               serialized[name] = value;
           }
       }
   }

   return serialized;
};

要将属性值重置回课程,您有两个选择:

  • 在您的类中创建一个函数,该函数根据序列化的JSON创建一个有效的对象实例。
  • 创建一个unserialize方法,并使用setter将JSON映射到您的类。

示例:

function unserialize(obj, emptyClass) {
   // Check emptyClass for setters and map the data from obj to it.
   return 'class instance';
}

答案 3 :(得分:1)

通常,您使用JSON执行此操作,该浏览器/语言/库/等广泛支持。唯一的问题是JSON不支持函数 - 但你真的需要序列化吗?

答案 4 :(得分:0)

我以前必须支持与此类似的功能。我最终将函数的名称保存为字符串并将其序列化为JSON。然后,当我回到客户端时,我使用this question中发布的帮助程序执行该函数。

如果有人有更好的方法来解决这个问题,我想看到它!

答案 5 :(得分:-1)

我最近不得不为这个问题找到解决方案。我相信它可以改进。

首先,我创建了一个用于实例化“serialisable”对象的模块。

function MyObj(serialised){
    this.val = "";
    if(serialised){
        var unserialised = JSON.parse(serialised);
        for (var i in unserialised) {
            this[i] = unserialised[i];
        }
    }
}

MyObj.prototype.myMethod = function () { return this.val;};

module.exports = MyObj;

您当然必须考虑错误处理和其他验证。