Створити об'єкт з масиву


92

Я хочу створити об'єкт зі списку масиву. У мене є динамічний масив, який, мабуть, має виглядати так:

var dynamicArray = ["2007", "2008", "2009", "2010"];

а з деяким javascript es6 я хочу зробити такий об’єкт:

const obj = {
    2007: {
        x: width / 5,
        y: height / 2
    },
    2008: {
        x: (2 / 5) * width,
        y: height / 2
    },
    2009: {
        x: (3 / 5) * width,
        y: height / 2
    },
    2010: {
        x: (4 / 5) * width,
        y: height / 2
    }
}

не турбуйтеся про внутрішні об'єкти, а просто хотіли зробити таку структуру:

 obj = {
      2007: ...,
      2008: ...,
      ...
    }

Будь ласка, допоможіть, дякую.


2
Добре. Що ви пробували? Де ти застряг? Які дослідження ви зробили? Ви дивились на це , наприклад?
TJ Crowder,

Відповіді:


218

Просто

 const obj = {};

 for (const key of yourArray) {
      obj[key] = whatever;
 }

або якщо ви віддаєте перевагу "функціональному" стилю:

 const obj = yourArray.reduce((o, key) => Object.assign(o, {[key]: whatever}), {});

за допомогою сучасного оператора розповсюдження об’єктів:

const obj = yourArray.reduce((o, key) => ({ ...o, [key]: whatever}), {})

Приклад:

[
  { id: 10, color: "red" },
  { id: 20, color: "blue" },
  { id: 30, color: "green" }
].reduce((acc, cur) => ({ ...acc, [cur.color]: cur.id }), {})

Вихід:

{red: 10, blue: 20, green: 30}

Ось як це працює:

reduceініціалізується порожнім об'єктом (порожнім {}в кінці), отже, першими ітераційними змінними є acc = {} cur = { id: 10, color: "red" }. Функція повертає об'єкт - ось чому тіло функції загортається в дужки => ({ ... }). Оператор розвороту нічого не робить на першій ітерації, тому red: 10встановлюється як перший елемент.

На другій ітерації змінні є acc = { red: 10 } cur = { id: 20, color: "blue" }. Тут оператор поширення розширюється acc і функція повертається { red: 10, blue: 20 }.

Третя ітерація acc = { red: 10, blue: 20 } cur = { id: 30, color: "green" }, тому при accрозповсюдженні всередині об’єкта наша функція повертає остаточне значення.


1
Дякую! Це спрацювало як потрібно. Я ніколи не знав про array.reduceфункцію.
Хуссейн Деггамвала

1
Якщо ви віддаєте перевагу функціональному стилю, і мені подобається, вам слід використовувати const. Насправді ви повинні використовувати його незалежно. Крім того, якщо у вас є доступ до синтаксису ES Next rest / spread (скажімо через TypeScript або Babel), ви можете писати const obj = yourArray.reduce((o, key) => ({ ...o, [key]: whatever}), {})і навіть уникати мутації насіння: p
Алуан Хаддад,

1
@AluanHaddad: гарна пропозиція, перетворено допис у CW, сміливо редагуйте.
georg

({... o, [ключ]: кандидатДок [ключ]}) .. де кандидатДок - це деяке пожо. Я хочу взяти лише значення, визначені у kandidatDoc. Але я плутаюся з цими дужками, здається, я не можу отримати повернення або твердження if, щоб спрацювати. Не могли б ви вказати мені у правильному напрямку - не злякався читати документацію.
терари

1
@cameck: дякую, пост CW, сміливо редагуйте.
georg

38

Нове Object.fromEntries, від ECMAScript 2019, робить ще простішим перетворення значень з масиву в ключі в об'єкті, як показано нижче

const dynamicArray = ["2007", "2008", "2009", "2010"];
const obj = Object.fromEntries(
  dynamicArray.map(year => [year, {
    something: "based",
    on: year
  }])
)

console.log(obj)


21

в js з функцією зменшення es6 для масиву я роблю це так

let x = [1,2,3]
let y = x.reduce((acc, elem) => {
  acc[elem] = elem // or what ever object you want inside
  return acc
}, {})
console.log(y) // {1:1, 2:2, 3:3}

3
ще коротше:[1, 2, 3].reduce((x, y)=>(x[y] = 1, x), {})
видання

5
var keys = ['key1', 'key2', 'key3']

var object = Object.assign({}, ...Object.entries({...keys}).map(([a,b]) => ({ [b]: 'someValue' })))
console.log(object)

Це дасть результат

{ key1: 'someValue', key2: 'someValue', key3: 'someValue' }

0

Я виявив, що насправді ви можете просто використовувати Object.assign()безпосередньо з оператором поширення. Не потрібно вводити більше складності з функцією reduceабо map.

Просто зробіть, Object.assign(...yourArray, {})і ви отримаєте бажаний результат. Якщо замість цього ви хочете об'єднати свій масив об'єктів в інший об'єкт, ви можете також зателефонувати, Object.assign(...yourArray, yourObject)і це також буде працювати чудово.

Ви також можете використовувати цей самий метод для об'єднання двох масивів в один об'єкт, навіть якщо один з масивів не містить об'єктів, а лише примітивні значення - однак, якщо ви це зробите, вам потрібно переконатися, що принаймні в одному з масивів містяться лише об'єкти як примітив буде за замовчуванням використовувати свій індекс як key, тому ви отримаєте помилки, якщо є дублікат ключа.

Однак для цілей операційних програм немає ризику таких помилок, оскільки він зливається з порожнім об'єктом, що є найбезпечнішим способом.

const arr = [
  { a: 0 },
  { c: 1 },
  { e: 2 },
];

const obj = Object.assign(...arr, {});

console.log(obj)

// Results to:
// Object { a: 0, c: 1, e: 2 }

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.