假设我有一个对象:

elmo = { 
  color: 'red',
  annoying: true,
  height: 'unknown',
  meta: { one: '1', two: '2'}
};

我想用它的属性子集创建一个新对象。

 // pseudo code
 subset = elmo.slice('color', 'height')

 //=> { color: 'red', height: 'unknown' }

我怎样才能做到呢?


当前回答

虽然它有点啰嗦,但通过使用Array.prototype.reduce,你可以完成其他人在2年前推荐的underscore/lodash。

var subset = ['color', 'height'].reduce(function(o, k) { o[k] = elmo[k]; return o; }, {});

这种方法从另一方面解决了这个问题:而不是获取一个对象并将属性名传递给它来提取,而是获取一个属性名数组并将它们简化为一个新对象。

While it's more verbose in the simplest case, a callback here is pretty handy, since you can easily meet some common requirements, e.g. change the 'color' property to 'colour' on the new object, flatten arrays, etc. -- any of the things you need to do when receiving an object from one service/library and building a new object needed somewhere else. While underscore/lodash are excellent, well-implemented libs, this is my preferred approach for less vendor-reliance, and a simpler, more consistent approach when my subset-building logic gets more complex.

编辑:es7版本相同:

const subset = ['color', 'height'].reduce((a, e) => (a[e] = elmo[e], a), {});

编辑:这也是咖喱的一个很好的例子!让'pick'函数返回另一个函数。

const pick = (...props) => o => props.reduce((a, e) => ({ ...a, [e]: o[e] }), {});

上面的方法非常接近于另一种方法,除了它让你在运行中构建一个“picker”。如。

pick('color', 'height')(elmo);

这种方法的特别之处在于,你可以很容易地将所选的“picks”传递到任何带有函数的对象中,例如Array#map:

[elmo, grover, bigBird].map(pick('color', 'height'));
// [
//   { color: 'red', height: 'short' },
//   { color: 'blue', height: 'medium' },
//   { color: 'yellow', height: 'tall' },
// ]

其他回答

使用对象解构和属性简写

Const对象= {a: 5, b: 6, c: 7}; const = (({a、c }) => ({ a、c}))(对象); console.log(选择);// {a: 5, c: 7}


来自Philipp Kewisch:

这实际上只是一个被即时调用的匿名函数。所有这些都可以在MDN上的解构分配页面上找到。这是一个展开的形式

Let unwrap = ({a, c}) => ({a, c}); 让unwrap2 = function({a, c}){返回{a, c};}; Let selected = unwrap({a: 5, b: 6, c: 7}); 让picke2 = unwrap2({a: 5, b: 6, c: 7}) console.log(选) console.log (picked2)

我认为这就是你的答案。(以及所有正在寻找它的人)。

const object = { a: 5, b: 6, c: 7  };
const subset = (({ a, c }) => ({ a, c }))(object);
console.log(subset); // { a: 5, c: 7 }

只是另一种方式……

var elmo = { 
  color: 'red',
  annoying: true,
  height: 'unknown',
  meta: { one: '1', two: '2'}
}

var subset = [elmo].map(x => ({
  color: x.color,
  height: x.height
}))[0]

你可以在Objects =)数组中使用这个函数

我想在这里提到一个非常好的策展:

pick-es2019.js

Object.fromEntries(
  Object.entries(obj)
  .filter(([key]) => ['whitelisted', 'keys'].includes(key))
);

pick-es2017.js

Object.entries(obj)
.filter(([key]) => ['whitelisted', 'keys'].includes(key))
.reduce((obj, [key, val]) => Object.assign(obj, { [key]: val }), {});

pick-es2015.js

Object.keys(obj)
.filter((key) => ['whitelisted', 'keys'].indexOf(key) >= 0)
.reduce((newObj, key) => Object.assign(newObj, { [key]: obj[key] }), {})

omit-es2019.js

Object.fromEntries(
  Object.entries(obj)
  .filter(([key]) => !['blacklisted', 'keys'].includes(key))
);

omit-es2017.js

Object.entries(obj)
.filter(([key]) => !['blacklisted', 'keys'].includes(key))
.reduce((obj, [key, val]) => Object.assign(obj, { [key]: val }), {});

omit-es2015.js

Object.keys(obj)
.filter((key) => ['blacklisted', 'keys'].indexOf(key) < 0)
.reduce((newObj, key) => Object.assign(newObj, { [key]: obj[key] }), {})
function splice()
{
    var ret = new Object();

    for(i = 1; i < arguments.length; i++)
        ret[arguments[i]] = arguments[0][arguments[i]];

    return ret;
}

var answer = splice(elmo, "color", "height");