繁体   English   中英

复制JS对象并过滤掉某些属性的最简单方法

[英]Simplest way to copy JS object and filter out certain properties

如果我有一个JS对象,并且我想创建一个新对象,该对象将复制所有属性(除了需要过滤掉的属性黑名单),最简单的方法是什么?

所以我会做类似的事情

originalObject.copyAndFilter('a', 'b')

它将获取原始对象,将其复制,并确保属性ab不在新对象中。

我正在通过Babel使用ES2015 / 2016,因此如果它提供了更简单的方法也可以使用。

您可以使用“ Set并删除不需要的属性。

 var object = { a: 1, b: 2, c: 3, d: 4 }, filteredObject = {}, p = new Set(Object.keys(object)); blacklist = ['a', 'b']; blacklist.forEach(a => p.delete(a)); [...p].forEach(k => filteredObject[k] = object[k]); console.log(filteredObject); 

嗯,没有简单的本机方法,我会将键转换为数组,对其进行过滤,然后创建一个新对象:

 const obj = {a: 'foo', b: 'bar', c: 'baz'}; const blacklist = ['a', 'b']; const keys = Object.keys(obj); const filteredKeys = keys.filter(key => !blacklist.includes(key)); const filteredObj = filteredKeys.reduce((result, key) => { result[key] = obj[key]; return result; }, {}); console.log(filteredObj); 

您可以仅遍历对象键并创建一个新对象。 您甚至可以使用for...in 这将具有所有浏览器都支持的更多优势。

 var obj = {a: 'foo', b: 'bar', c: 'baz'}; var blackListKeys = ['a', 'b','z']; var obj2 = {} for(var k in obj){ if(blackListKeys.indexOf(k) === -1) obj2[k] = obj[k]; } console.log(obj2) 

 var obj = {foo: 1, a: 2, b:3} var newObj = {} var blacklist = ['a', 'b'] for(let [key, value] of Object.entries(obj)) { !blacklist.includes(key) && (newObj[key] = value) } console.log(newObj) 

变量较少:

 var obj = {foo: 1, a: 2, b: 3} var newObj = Object.entries(obj) .filter(([key, val]) => !['a', 'b'].includes(key)) .reduce((newObj, [key, value]) => (newObj[key] = value, newObj), {}) console.log(newObj) 

我认为Object.assign是最好的ES5实用程序,只需很少的额外逻辑即可实现:

function copyAndFilter(...args){ 
    var copy = Object.assign( {} , this);

    args.forEach(prop => { 
        delete copy[prop];
    }); return copy;
}

然后:

var a = {foo : 'foo' , bar : 'bar'};
a.copyAndFilter = /* function definition above*/
a.copyAndFilter('foo');// { bar : 'bar' }

这里有两个问题:

第一个实际上是复制没有引用的对象。

如果仅针对对象键进行循环并从原始对象中对其值进行赋值(如果这些值也是对象),则最终将引用该对象(甚至数组),而不是对其自身进行复制。 因此,您需要检测到该问题并递归调用copy_object函数以避免引用。

幸运的是,该问题已经在某些库中得到了解决,这些库提供了对象的extend()函数,例如npm (服务器端)和jQuery (浏览器)。

诀窍仅在于扩展新创建的对象:

var dst_object = extend({}, src_object);

第二个问题是避免不需要的密钥。

这里有可能的方法:一种是以提供黑名单功能的方式完全重新实现上述的extend()函数。

...而第二个(而且更不容易出错)是在复制对象之后简单地删除不需要的键。 如果它们不是巨大的数据结构,那么开销将是微不足道的。

例:

// npm install --save extend
var extend = require("extend");
function oClone(target, blacklist) {
    var dest = extend({}, target);
    if (blacklist) {
        for (var i=0; i<blacklist.length; i++) {
            delete (dest[blacklist[i]]);
        };
    };
    return dest;
};

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM