Javascript 在Angular 2中复制对象的最佳方式是什么?

Javascript 在Angular 2中复制对象的最佳方式是什么?,javascript,angularjs,angular,Javascript,Angularjs,Angular,Angular 1.x具有全局Angular对象上的方法,如Angular.copy、Angular.shallowCopy(更不用说Angular.forEach等其他方法),但在Angular 2中似乎没有等效的版本。也许只是没有记录在案。如果Angular 2不打算提供这些UTIL,那么获得该功能的最佳方式是什么 我知道我可以使用angular 1.x中的逻辑推出自己的浅层复制方法: function shallowCopy(src, dst) { if (isArray(src))

Angular 1.x具有全局Angular对象上的方法,如Angular.copy、Angular.shallowCopy(更不用说Angular.forEach等其他方法),但在Angular 2中似乎没有等效的版本。也许只是没有记录在案。如果Angular 2不打算提供这些UTIL,那么获得该功能的最佳方式是什么

我知道我可以使用angular 1.x中的逻辑推出自己的浅层复制方法:

function shallowCopy(src, dst) {
  if (isArray(src)) {
    dst = dst || [];

    for (var i = 0, ii = src.length; i < ii; i++) {
      dst[i] = src[i];
    }
  } else if (isObject(src)) {
    dst = dst || {};

    for (var key in src) {
      if (!(key.charAt(0) === '$' && key.charAt(1) === '$')) {
        dst[key] = src[key];
      }
    }
  }

  return dst || src;
}
函数浅拷贝(src、dst){
if(isArray(src)){
dst=dst | |[];
对于(变量i=0,ii=src.length;i

但是深度复制逻辑要复杂得多(显然)

为什么不简单地复制angular 1 copy函数呢

从源代码(需要修改一些东西,比如对错误处理程序的调用,但基本上:)

函数副本(源、目标、stackSource、stackDest){
if(isWindow(源)| | isScope(源)){
投掷NGMiner(“cpws”,
“无法复制!不支持复制窗口或范围实例。”);
}
if(isTypedArray(目的地)){
投掷NGMiner(“cpta”,
“无法复制!无法变异TypedArray目标。”);
}
如果(!目的地){
目的地=来源;
if(isObject(源)){
var指数;
if(stackSource&(index=stackSource.indexOf(source))!=-1){
返回stackDest[索引];
}
//TypedArray、Date和RegExp具有特定的复制功能,必须
//返回前推到堆栈上。
//数组和其他对象创建基对象并递归以复制子对象
//数组/对象在递归时将被推送到堆栈上。
if(isArray(源)){
返回副本(来源,[],stackSource,stackDest);
}else if(isTypedArray(源)){
目的地=新的源。构造函数(源);
}else if(isDate(源)){
destination=新日期(source.getTime());
}else if(isRegExp(源)){
destination=newregexp(source.source,source.toString().match(/[^\/]*$/)[0]);
destination.lastIndex=source.lastIndex;
}else if(isFunction(source.cloneNode)){
destination=source.cloneNode(true);
}否则{
var emptyObject=Object.create(getPrototypeOf(source));
返回副本(源、emptyObject、stackSource、stackDest);
}
if(stackDest){
stackSource.push(source);
stackDest.push(目的地);
}
}
}否则{
如果(源===目的地)抛出NGMiner('cpi',
“无法复制!源和目标相同。”);
stackSource=stackSource | |[];
stackDest=stackDest | |[];
if(isObject(源)){
stackSource.push(source);
stackDest.push(目的地);
}
var结果,关键;
if(isArray(源)){
destination.length=0;
对于(变量i=0;i
当对象是数组时,我使用:

copyOfArray=originalArray.slice(0,originalArray.length)

其中,
originalArray
是原始数组对象


内置javascript
array.slice(start,end)
函数将数组的子集作为新的数组对象()返回。将开始和结束边界设置为原始数组的大小将返回整个数组的副本。

我知道我可以复制问题中提到的Angular 1版本。但问题是这是否是最好的办法。如果您查看该代码,您将看到有许多对其他方法的调用也必须复制(isArray、isTypedArray、isDate、isRegExp等)。沿着这条路走实际上是可以的,但是如果Angular 2有一些类来处理它,那就更好了。或者其他一些可以使用的首选库也可以工作。任何富应用程序都需要深度复制,所以,是的,您需要一种方法来实现它。现在您可以使用jQuery的deep extends,或者lodash的cloneDeep,如果您愿意的话,而不是使用copypasting ng1方法…是的。。。我刚开始只是使用jQuery,但是如果angular提供了一种方法,这样做会更好,这样您就不必依赖于另一个库;似乎有效。可能在某个地方有一个对象克隆实用程序,但还没有文档记录。@SangwinGawande使用Angula时删除javascript标记的意义是什么
function copy(source, destination, stackSource, stackDest) {
  if (isWindow(source) || isScope(source)) {
    throw ngMinErr('cpws',
      "Can't copy! Making copies of Window or Scope instances is not supported.");
  }
  if (isTypedArray(destination)) {
    throw ngMinErr('cpta',
      "Can't copy! TypedArray destination cannot be mutated.");
  }

  if (!destination) {
    destination = source;
    if (isObject(source)) {
      var index;
      if (stackSource && (index = stackSource.indexOf(source)) !== -1) {
        return stackDest[index];
      }

      // TypedArray, Date and RegExp have specific copy functionality and must be
      // pushed onto the stack before returning.
      // Array and other objects create the base object and recurse to copy child
      // objects. The array/object will be pushed onto the stack when recursed.
      if (isArray(source)) {
        return copy(source, [], stackSource, stackDest);
      } else if (isTypedArray(source)) {
        destination = new source.constructor(source);
      } else if (isDate(source)) {
        destination = new Date(source.getTime());
      } else if (isRegExp(source)) {
        destination = new RegExp(source.source, source.toString().match(/[^\/]*$/)[0]);
        destination.lastIndex = source.lastIndex;
      } else if (isFunction(source.cloneNode)) {
          destination = source.cloneNode(true);
      } else {
        var emptyObject = Object.create(getPrototypeOf(source));
        return copy(source, emptyObject, stackSource, stackDest);
      }

      if (stackDest) {
        stackSource.push(source);
        stackDest.push(destination);
      }
    }
  } else {
    if (source === destination) throw ngMinErr('cpi',
      "Can't copy! Source and destination are identical.");

    stackSource = stackSource || [];
    stackDest = stackDest || [];

    if (isObject(source)) {
      stackSource.push(source);
      stackDest.push(destination);
    }

    var result, key;
    if (isArray(source)) {
      destination.length = 0;
      for (var i = 0; i < source.length; i++) {
        destination.push(copy(source[i], null, stackSource, stackDest));
      }
    } else {
      var h = destination.$$hashKey;
      if (isArray(destination)) {
        destination.length = 0;
      } else {
        forEach(destination, function(value, key) {
          delete destination[key];
        });
      }
      if (isBlankObject(source)) {
        // createMap() fast path --- Safe to avoid hasOwnProperty check because prototype chain is empty
        for (key in source) {
          destination[key] = copy(source[key], null, stackSource, stackDest);
        }
      } else if (source && typeof source.hasOwnProperty === 'function') {
        // Slow path, which must rely on hasOwnProperty
        for (key in source) {
          if (source.hasOwnProperty(key)) {
            destination[key] = copy(source[key], null, stackSource, stackDest);
          }
        }
      } else {
        // Slowest path --- hasOwnProperty can't be called as a method
        for (key in source) {
          if (hasOwnProperty.call(source, key)) {
            destination[key] = copy(source[key], null, stackSource, stackDest);
          }
        }
      }
      setHashKey(destination,h);
    }
  }
  return destination;
}