深度克隆没有一些字段

我们有下一个javascript对象。 现在我想克隆它但没有一些字段。 例如,我想要没有字段"lastName""cars.age"克隆对象
输入

 { "firstName":"Fred", "lastName":"McDonald", "cars":[ { "type":"mersedes", "age":5 }, { "model":"bmw", "age":10 } ] } 

输出 (克隆)

 { "firstName":"Fred", "cars":[ { "model":"mersedes" }, { "model":"bmw" } ] } 

我可以做点什么

 var human = myJson var clone = $.extend(true, {}, human) delete clone.lastName _.each(clone.cars, function(car)) { delete car.age } 

你知道更容易解决方案吗?

如果您不介意添加到对象原型,这是一个简单的解决方案。 您可能希望将其修改为一些供您自己使用。

 Object.prototype.deepOmit = function(blackList) { if (!_.isArray(blackList)) { throw new Error("deepOmit(): argument must be an Array"); } var copy = _.omit(this, blackList); _.each(blackList, function(arg) { if (_.contains(arg, '.')) { var key = _.first(arg.split('.')); var last = arg.split('.').slice(1); copy[key] = copy[key].deepOmit(last); } }); return copy; }; Array.prototype.deepOmit = function(blackList) { if (!_.isArray(blackList)) { throw new Error("deepOmit(): argument must be an Array"); } return _.map(this, function(item) { return item.deepOmit(blackList); }); }; 

然后当你有一个像这样的对象:

 var personThatOwnsCars = { "firstName":"Fred", "lastName":"McDonald", "cars":[ { "type":"mersedes", "age":5 }, { "model":"bmw", "age":10 } ] }; 

你可以这样做魔法。

 personThatOwnsCars.deepOmit(["firstName", "cars.age"]); 

甚至像这样的魔法!

 [person1, person2].deepOmit(["firstName", "cars.age"]); 

这是一个独立的函数,取决于我写的lodash /下划线也是如此。

它为对象或数组中的每个(value,indexOrKey)对调用一个回调,如果为true,则在结果对象中省略该对。

在访问该值之后调用回调,因此您可以省略与您的条件匹配的整个子树。

 function deepOmit(sourceObj, callback, thisArg) { var destObj, i, shouldOmit, newValue; if (_.isUndefined(sourceObj)) { return undefined; } callback = thisArg ? _.bind(callback, thisArg) : callback; if (_.isPlainObject(sourceObj)) { destObj = {}; _.forOwn(sourceObj, function(value, key) { newValue = deepOmit(value, callback); shouldOmit = callback(newValue, key); if (!shouldOmit) { destObj[key] = newValue; } }); } else if (_.isArray(sourceObj)) { destObj = []; for (i = 0; i  

一些样品

 var sourceObj = { a1: [ undefined, {}, { o: undefined } ], a2: [ 1, undefined ], o: { s: 's' } }; deepOmit(sourceObj, function (value) { return value === undefined; }); //=> { a1: [ {}, {} ], a2: [ 1 ], o: { s: 's' }} //omit empty objects and arrays too deepOmit(sourceObj, function (value) { return value === undefined || (_.isPlainObject(value) && !_.keys(value).length) || (_.isArray(value) && !value.length); }); //=> { a2: [ 1 ], o: { s: 's' }} //indexOrKey is the string key or the numeric index if the object is array deepOmit([ 0, 1, 2, 3, 4 ], function (value, indexOrKey) { return indexOrKey % 2; }); //=> [ 0, 2, 4 ]