Преобразование массива в объект

Каков наилучший способ преобразования:

['a','b','c']

в

{
  0: 'a',
  1: 'b',
  2: 'c'
}

Ответ 1

ECMAScript 6 представляет легко заполняемый Object.assign:

Метод Object.assign() используется для копирования значений всех перечисляемых собственных свойств из одного или нескольких исходных объектов в целевой объект. Он вернет целевой объект.

Object.assign({}, ['a','b','c']); // {0:"a", 1:"b", 2:"c"}

Собственное свойство length массива не копируется, поскольку оно не перечисляемо.

Кроме того, вы можете использовать синтаксис ES6 для достижения того же результата:

{ ...['a', 'b', 'c'] }

Ответ 2

С такой функцией:

function toObject(arr) {
  var rv = {};
  for (var i = 0; i < arr.length; ++i)
    rv[i] = arr[i];
  return rv;
}

Ваш массив уже является более или менее просто объектом, но массивы имеют некоторое "интересное" и особое поведение в отношении свойств с целыми именами. Вышеуказанное даст вам простой объект.

edit oh также вы можете учесть "дыры" в массиве:

function toObject(arr) {
  var rv = {};
  for (var i = 0; i < arr.length; ++i)
    if (arr[i] !== undefined) rv[i] = arr[i];
  return rv;
}

В современных сценариях JavaScript вы можете использовать метод .reduce():

var obj = arr.reduce(function(acc, cur, i) {
  acc[i] = cur;
  return acc;
}, {});

Это также позволяет избежать "дыр" в массиве, так как работает .reduce().

Ответ 3

Вы можете использовать аккумулятор aka reduce.

['a','b','c'].reduce(function(result, item, index, array) {
  result[index] = item; //a, b, c
  return result;
}, {}) //watch out the empty {}, which is passed as "result"

Передайте пустой объект {} в качестве отправной точки; затем "увеличивать" этот объект поэтапно. В конце итераций result будет {"0": "a", "1": "b", "2": "c"}

Если ваш массив представляет собой набор объектов пары "ключ-значение":

[{ a: 1},{ b: 2},{ c: 3}].reduce(function(result, item) {
  var key = Object.keys(item)[0]; //first property: a, b, c
  result[key] = item[key];
  return result;
}, {});

произведет: {a: 1, b: 2, c: 3}

Для полноты, reduceRight позволяет вам перебирать массив в обратном порядке:

[{ a: 1},{ b: 2},{ c: 3}].reduceRight(/* same implementation as above */)

будет производить: {c:3, b:2, a:1}

Ваш аккумулятор может быть любого типа для вас. Например, чтобы поменять ключ и значение вашего объекта в массиве, пройдите []:

[{ a: 1},{ b: 2},{ c: 3}].reduce(function(result, item, index) {
  var key = Object.keys(item)[0]; //first property: a, b, c
  var value = item[key];
  var obj = {};
  obj[value] = key;
  result.push(obj);
  return result;
}, []); //an empty array

произведет: [{1: "a"}, {2: "b"}, {3: "c"}]

В отличие от map, reduce не может использоваться как отображение 1-1. Вы полностью контролируете элементы, которые хотите включить или исключить. Поэтому reduce позволяет достичь того, что делает filter, что делает reduce очень универсальным:

[{ a: 1},{ b: 2},{ c: 3}].reduce(function(result, item, index) {
  if(index !== 0) { //skip the first item
    result.push(item);
  }
  return result;
}, []); //an empty array

будет производить: [{2: "b"}, {3: "c"}]

Внимание: reduce и Object.key являются частью ECMA 5th edition; вы должны предоставить polyfill для браузеров, которые их не поддерживают (особенно IE8).

См. реализацию по умолчанию Mozilla.

Ответ 4

Если вы используете jquery:

$.extend({}, ['a', 'b', 'c']);

Ответ 5

Для полноты распространения ECMAScript 2015 (ES6). Потребуется либо транспортер (Babel), либо среда, работающая как минимум на ES6.

console.log(
   { ...['a', 'b', 'c'] }
)

Ответ 6

Я бы, вероятно, написал это так (потому что очень редко я не буду иметь библиотеку underscorejs под рукой):

var _ = require('underscore');

var a = [ 'a', 'b', 'c' ];
var obj = _.extend({}, a);
console.log(obj);
// prints { '0': 'a', '1': 'b', '2': 'c' }

Ответ 7

Вот метод O (1) ES2015 только для полноты.

var arr = [1, 2, 3, 4, 5]; // array, already an object
Object.setPrototypeOf(arr, Object.prototype); // now no longer an array, still an object

Ответ 8

Удивленно не видеть -

Object.assign({}, your_array)

Ответ 9

мы можем использовать функцию Object.assign и array.reduce для преобразования массива в объект.

var arr = [{a:{b:1}},{c:{d:2}}] 
var newObj = arr.reduce((a, b) => Object.assign(a, b), {})

console.log(newObj)

Ответ 10

Object.assign({}, ['one', 'two']); // {0: 'one', 1: 'two'}

Простым способом в современном JavaScript является использование Object.assign(), который ничего не делает, кроме копирования ключа: значение от одного объекта к другому. В нашем случае Array передает свойства новым {}.

Ответ 11

Я закончил использование оператора распространения объектов, так как он является частью стандарта ECMAScript 2015 (ES6).

const array = ['a', 'b', 'c'];
console.log({...array});
// it outputs {0:'a', 1:'b', 2:'c'}

В качестве примера можно привести следующую скрипку.

Ответ 12

Пять лет спустя, там хороший способ:)

Object.assign был представлен в ECMAScript 2015.

Object.assign({}, ['a', 'b', 'c'])
// {'0':'a', '1':'b', '2':'c'}

Ответ 13

Используя javascript#forEach, можно сделать это

var result = {},
    attributes = ['a', 'b','c'];

attributes.forEach(function(prop,index) {
  result[index] = prop;
});

с ECMA6:

attributes.forEach((prop,index)=>result[index] = prop);

Ответ 14

Если вы используете ES6, вы можете использовать Object.assign и оператор с расширением

{ ...['a', 'b', 'c'] }

Если у вас есть вложенный массив вроде

var arr=[[1,2,3,4]]
Object.assign(...arr.map(d => ({[d[0]]: d[1]})))

Ответ 15

вы можете использовать оператор спреда

x = [1,2,3,10]
{...x} // {0:1, 1:2, 2:3, 3:10}

Ответ 16

Для ES2016, оператор распространения для объектов. Примечание: это после ES6 и поэтому необходимо настроить транспортер.

const arr = ['a', 'b', 'c'];
const obj = {...arr}; // -> {0: "a", 1: "b", 2: "c"} 

Ответ 17

FWIW, еще один недавний подход - использовать новые Object.fromEntries вместе с Object.entries следующим образом:

const arr = ['a','b','c'];
arr[-2] = 'd';
arr.hello = 'e';
arr.length = 17;
const obj = Object.fromEntries(Object.entries(arr));

... который позволяет избежать хранения разреженных элементов массива как undefined или null и сохраняет неиндексные (например, неположительные целые/нечисловые) ключи.

Однако можно добавить arr.length, поскольку это не включено:

obj.length = arr.length;

Ответ 18

Быстрый и грязный:

var obj = {},
  arr = ['a','b','c'],
  l = arr.length; 

while( l && (obj[--l] = arr.pop() ) ){};

Ответ 19

Быстрая и грязная # 2:

var i = 0
  , s = {}
  , a = ['A', 'B', 'C'];

while( a[i] ) { s[i] = a[i++] };

Ответ 20

С Lodash 3.0.0 вы можете использовать _. toPlainObject

var obj = _.toPlainObject(['a', 'b', 'c']);
console.log(obj);
<script src="https://cdn.jsdelivr.net/lodash/4.16.4/lodash.min.js"></script>

Ответ 21

Это позволяет вам генерировать из массива объект с ключами, которые вы определяете, в том порядке, в котором вы хотите.

Array.prototype.toObject = function(keys){
    var obj = {};
    var tmp = this; // we want the original array intact.
    if(keys.length == this.length){
        var c = this.length-1;
        while( c>=0 ){
            obj[ keys[ c ] ] = tmp[c];
            c--;
        }
    }
    return obj;
};

result = ["cheese","paint",14,8].toObject([0,"onion",4,99]);

console.log(">>> :" + result.onion); выводит "paint", функция должна иметь массивы равной длины или вы получаете пустой объект.

Вот обновленный метод

Array.prototype.toObject = function(keys){
    var obj = {};
    if( keys.length == this.length)
        while( keys.length )
            obj[ keys.pop() ] = this[ keys.length ];
    return obj;
};

Ответ 22

Здесь рекурсивная функция, которую я только что написал. Это просто и хорошо работает.

// Convert array to object
var convArrToObj = function(array){
    var thisEleObj = new Object();
    if(typeof array == "object"){
        for(var i in array){
            var thisEle = convArrToObj(array[i]);
            thisEleObj[i] = thisEle;
        }
    }else {
        thisEleObj = array;
    }
    return thisEleObj;
}

Здесь пример (jsFiddle):

var array = new Array();
array.a = 123;
array.b = 234;
array.c = 345;
var array2 = new Array();
array2.a = 321;
array2.b = 432;
array2.c = 543;
var array3 = new Array();
array3.a = 132;
array3.b = 243;
array3.c = 354;
var array4 = new Array();
array4.a = 312;
array4.b = 423;
array4.c = 534;
var array5 = new Array();
array5.a = 112;
array5.b = 223;
array5.c = 334;

array.d = array2;
array4.d = array5;
array3.d = array4;
array.e = array3;


console.log(array);

// Convert array to object
var convArrToObj = function(array){
    var thisEleObj = new Object();
    if(typeof array == "object"){
        for(var i in array){
            var thisEle = convArrToObj(array[i]);
            thisEleObj[i] = thisEle;
        }
    }else {
        thisEleObj = array;
    }
    return thisEleObj;
}
console.log(convArrToObj(array));

Результаты: Recursive Array to Object

Ответ 23

.reduce((o,v,i)=>(o[i]=v,o), {})

[документы]

или более подробный

var trAr2Obj = function (arr) {return arr.reduce((o,v,i)=>(o[i]=v,o), {});}

или

var transposeAr2Obj = arr=>arr.reduce((o,v,i)=>(o[i]=v,o), {})

кратчайший с ванилью JS

JSON.stringify([["a", "X"], ["b", "Y"]].reduce((o,v,i)=>{return o[i]=v,o}, {}))
=> "{"0":["a","X"],"1":["b","Y"]}"

более сложный пример

[["a", "X"], ["b", "Y"]].reduce((o,v,i)=>{return o[v[0]]=v.slice(1)[0],o}, {})
=> Object {a: "X", b: "Y"}

еще короче (используя function(e) {console.log(e); return e;} === (e)=>(console.log(e),e))

 nodejs
> [[1, 2, 3], [3,4,5]].reduce((o,v,i)=>(o[v[0]]=v.slice(1),o), {})
{ '1': [ 2, 3 ], '3': [ 4, 5 ] }

[/документы]

Ответ 24

Я бы сделал это просто с Array.of(). Array of имеет возможность использовать его как конструктор.

ПРИМЕЧАНИЕ 2 Функция представляет собой намеренно общий метод factory; Это не требует, чтобы это значение было конструктором Array. Поэтому он может быть передан или унаследован другими конструкторами который может быть вызван с помощью одного числового аргумента.

Таким образом, мы можем привязать Array.of() к функции и сгенерировать массив, подобный объекту.

function dummy(){};
var thingy = Array.of.apply(dummy,[1,2,3,4]);
console.log(thingy);

Ответ 25

Если вы можете использовать Map или Object.assign, это очень просто.

Создайте массив:

const languages = ['css', 'javascript', 'php', 'html'];

Ниже создается объект с индексом в виде ключей:

Object.assign({}, languages)

Повторите то же, что и выше, с помощью Maps

Преобразует объект на основе индекса {0 : 'css'} и т.д.

const indexMap = new Map(languages.map((name, i) => [i, name] ));
indexMap.get(1) // javascript

Преобразовать объект на основе значения {css : 'css is great'} и т.д.

const valueMap = new Map(languages.map(name => [name, `${name} is great!`] ));
valueMap.get('css') // css is great

Ответ 26

let i = 0;
let myArray = ["first", "second", "third", "fourth"];

const arrayToObject = (arr) =>
    Object.assign({}, ...arr.map(item => ({[i++]: item})));

console.log(arrayToObject(myArray));

Ответ 27

ES5 - Решение:

Используя функцию-прототип Array "push" и "apply", вы можете заполнить объект элементами массива.

var arr = ['a','b','c'];
var obj = new Object();
Array.prototype.push.apply(obj, arr);
console.log(obj);    // { '0': 'a', '1': 'b', '2': 'c', length: 3 }
console.log(obj[2]); // c

Ответ 28

Вы можете использовать такую ​​функцию:

var toObject = function(array) {
    var o = {};
    for (var property in array) {
        if (String(property >>> 0) == property && property >>> 0 != 0xffffffff) {
            o[i] = array[i];
        }
    }
    return o;
};

Это должно обрабатывать разреженные массивы более эффективно.

Ответ 29

Здесь решение в coffeescript

arrayToObj = (arr) ->
  obj = {}
  for v,i in arr
    obj[i] = v if v?
  obj

Ответ 30

Если вы используете angularjs, вы можете использовать angular.extend, тот же эффект с $.extend jquery.

var newObj = {};
angular.extend(newObj, ['a','b','c']);