4

我希望你能帮助我。

我想制作这个对象用户的深层副本。

function clone(obj) {
    if (null == obj || "object" != typeof obj)
        return obj;
    var copy = obj.constructor();
    for (var attr in obj) {
        if (obj.hasOwnProperty(attr))
            copy[attr] = obj[attr];
    }
  return copy;
}

var User = {
    _firstName: 'robert',

    get firstName() {
        return this._firstName;
    },
    set firstName(val) {
        this._firstName = val;
    },

    affFirstName: function() {
        console.log(this._firstName);
    },
};

console.log(User);
var User2 = clone(User);    
console.log(User2);

此功能克隆不起作用(例如,请参见小提琴)

此副本创建名称为 get 和 set 的新变量。

不复制设置和获取运算符。

但是函数 affFirstName() 被很好地复制了。

你有解决方案吗 ?

4

2 回答 2

7

在 ES5 中,您可以使用Object.getOwnPropertyDescriptor获取对象上可能存在的 getter 和 setter 的副本。

然后,您可以将这些描述符传递Object.defineProperty给以在新对象上重新创建它们。

请注意,如果这些 getter 或 setter 依赖于词法范围的变量,则新克隆将与原始对象共享这些变量。新对象将不会获得这些变量的自己的副本。

于 2013-07-04T15:11:43.853 回答
2
function clone(obj) {
  if (null == obj || "object" != typeof obj)
    return obj;
  var copy = obj.constructor();
  for (var attr in obj) {
    if (obj.hasOwnProperty(attr)) {
      if (Object.getOwnPropertyDescriptor(obj, attr).value instanceof Object) {
        copy[attr] = clone(obj[attr]);
      }
      else {
        Object.defineProperty(copy, attr, Object.getOwnPropertyDescriptor(obj,attr));
      }
    }
  }
  return copy;
}

更正的克隆功能可使用操作符获取和设置进行深层复制。

于 2013-07-04T15:32:56.547 回答