0

This is obviously straight-forward using traditional loops, but I'm curious if anyone can think of a nice, compact way of doing it with destructuring and the spread operator.

For example, let's say I have

const foo = { a: 1, b: 2, c: 3, d: 4 };
const list = ['a', 'd'];

I'd like to create bar = { a: 1, d: 4 }.

You could do something like

const bar = {};
list.forEach((p) => { bar.p = list.p; });

But I'm wondering if anyone has a slick one-liner using ES2015+. For example, you can do const { b, c, ...bar } = foo, but that's if you have the inverse known prior to runtime.

While the solution ideally would support a dynamic list of properties in an array, one with a statically known list is better than nothing. (For example, const bar = ({{ a, d }} = foo)

terry87
  • 275
  • 1
  • 3
  • 12
  • i mean... you could use reduce on list, but... it's not any more of a 1liner than forEach is. – Kevin B Mar 31 '17 at 17:33
  • `const bar = list.reduce((o, p) => (o[p] = foo[p], o), {});` – 4castle Mar 31 '17 at 17:33
  • This depends -- it looks like you're making a clone of the object. If a shallow copy works, you can use `const bar = Object.assign({}, list);` (sort of, depends on your loop) to make a copy by reference – Sterling Archer Mar 31 '17 at 17:33
  • `let bar = (x => {list.map( k => x[k]=foo[k] );return x;})({});` – adeneo Mar 31 '17 at 17:45
  • @KevinB Any reason you reopened it? If there was an ES6 way to do it purely with destructuring, it would be on that question. – 4castle Mar 31 '17 at 17:45
  • It's certainly similar, but it isn't a dupe of either. – Kevin B Mar 31 '17 at 17:45
  • @KevinB I don't see any point in keeping this as a unique question. It's got all the same solutions we've all seen before. – 4castle Mar 31 '17 at 17:47
  • Me either. doesn't mean it should be incorrectly closed. – Kevin B Mar 31 '17 at 17:47
  • 1
    @KevinB I disagree that it's an incorrect closure. This question has no unique value. – 4castle Mar 31 '17 at 17:48
  • `let bar = (x=>list.reduce((a,b)=>{return a[b]=foo[b],a},{}))({});` – adeneo Mar 31 '17 at 17:49
  • @KevinB It does indeed seem like a dup. The only difference I can see is that the OP is providing the list of properties to "pick" as an array of strings, but that's probably not essential to what he is trying to do. And the fact that he mentions destructuring would seem to indicate that he is open to that kind of solution, which is what the proposed dup provides. What is your thinking about why it's not a dup? –  Mar 31 '17 at 17:52
  • I agree that it's the same fundamental problem. I didn't find the old one when searching (very little keyword overlap). Hopefully the cross-listing will help. @torazaburo thanks for the elegant answer. – terry87 Mar 31 '17 at 17:59
  • @terry87 Please unaccept my answer so I can delete it, thanks. –  Mar 31 '17 at 18:28

1 Answers1

-1

The best I think you'll be able to do is with Array#reduce:

const foo = { a: 1, b: 2, c: 3, d: 4 };
const list = ['a', 'd'];

const bar = list.reduce((o, k) => (o[k] = foo[k], o), {})

console.log(bar)
gyre
  • 14,437
  • 1
  • 32
  • 46
  • @downvoter Care to explain why? – gyre Mar 31 '17 at 17:36
  • Probably a this-should-be-marked-as-dup-not-answered downvote, which some people do sometimes, and of which I am sometimes guilty myself. –  Mar 31 '17 at 17:53