Подтвердить что ты не робот

Как найти индекс объекта по ключу и значению в массиве javascript

Дано:

var peoples = [
  { "attr1": "bob", "attr2": "pizza" },
  { "attr1": "john", "attr2": "sushi" },
  { "attr1": "larry", "attr2": "hummus" }
];

Требуется:

Индекс объекта, где attr === value например attr1 === "john" или attr2 === "hummus"

Update: Пожалуйста, внимательно прочитайте мой вопрос, я не хочу искать объект через $.inArray, и я не хочу получать значение определенного атрибута объекта. Пожалуйста, рассмотрите это для своих ответов. Благодарю!

4b9b3361

Ответ 1

Функциональный подход

В эти дни все классные дети занимаются функциональным программированием (hello React users), поэтому я думал, что дам функциональное решение. На мой взгляд, это на самом деле намного приятнее, чем предваряемые циклы for и each, которые были предложены до сих пор, и с синтаксисом ES6 он довольно изящный.

Update

В настоящее время существует отличный способ сделать это findIndex, в котором используется функция, возвращающая true/false на основе того, элемент массива совпадает (как всегда, проверьте совместимость браузера).

var index = peoples.findIndex(function(person) {
  return person.attr1 == "john"
}

С синтаксисом ES6 вы можете написать это:

var index = peoples.findIndex(p => p.attr1 == "john")

(старый) функциональный подход

TL; DR

Если вы ищете index, где peoples[index].attr1 == "john" используйте:

var index = peoples.map(function(o) { return o.attr1; }).indexOf("john");

Описание

Шаг 1

Используйте .map(), чтобы получить массив значений с определенным ключом:

var values = object_array.map(function(o) { return o.your_key; });

Вышеприведенная строка выводит вас здесь:

var peoples = [
  { "attr1": "bob", "attr2": "pizza" },
  { "attr1": "john", "attr2": "sushi" },
  { "attr1": "larry", "attr2": "hummus" }
];

Здесь:

var values = [ "bob", "john", "larry" ];

Шаг 2

Теперь мы просто используем .indexOf(), чтобы найти индекс требуемого ключа (который, конечно, также является индексом объект, который мы ищем):

var index = values.indexOf(your_value);

Решение

Мы комбинируем все вышеперечисленное:

var index = peoples.map(function(o) { return o.attr1; }).indexOf("john");

Или, если вы предпочитаете синтаксис ES6:

var index = peoples.map((o) => o.attr1).indexOf("john");

Демо:

var peoples = [
  { "attr1": "bob", "attr2": "pizza" },
  { "attr1": "john", "attr2": "sushi" },
  { "attr1": "larry", "attr2": "hummus" }
];

var index = peoples.map(function(o) { return o.attr1; }).indexOf("john");
console.log("index of 'john': " + index);

var index = peoples.map((o) => o.attr1).indexOf("larry");
console.log("index of 'larry': " + index);

var index = peoples.map(function(o) { return o.attr1; }).indexOf("fred");
console.log("index of 'fred': " + index);

var index = peoples.map((o) => o.attr2).indexOf("pizza");
console.log("index of 'pizza' in 'attr2': " + index);

Ответ 2

Если вы хотите проверить сам объект, не мешая прототипу, используйте hasOwnProperty():

var getIndexIfObjWithOwnAttr = function(array, attr, value) {
    for(var i = 0; i < array.length; i++) {
        if(array[i].hasOwnProperty(attr) && array[i][attr] === value) {
            return i;
        }
    }
    return -1;
}

также включить атрибуты прототипа, используйте:

var getIndexIfObjWithAttr = function(array, attr, value) {
    for(var i = 0; i < array.length; i++) {
        if(array[i][attr] === value) {
            return i;
        }
    }
    return -1;
}

Ответ 3

Использование jQuery . each()

$.each(peoples, function(index, obj) {
   $.each(obj, function(attr, value) {
      console.log( attr + ' == ' + value );
   });
});

Рабочий пример

Использование for-loop:

for(var i = 0; i < peoples.length; i++) {
   for(var key in peoples[i] ) {
      console.log( key + ' == ' +  peoples[i][key]);
   }
}

Рабочий пример

Ответ 4

Не прямой ответ на ваш вопрос, хотя я считаю, что это хуже упоминает об этом, потому что ваш вопрос кажется подходящим в общем случае "получения вещей по имени в хранилище с ключом".

Если вы не слишком привязаны к тому, как реализуются "народы", более вероятным способом получения правильного парня может быть:

var peoples = {
  "bob":  { "dinner": "pizza" },
  "john": { "dinner": "sushi" },
  "larry" { "dinner": "hummus" }
};

// If people is implemented this way, then
// you can get values from their name, like :
var theGuy = peoples["john"];

// You can event get directly to the values
var thatGuysPrefferedDinner = peoples["john"].dinner;

Надеюсь, что если это не тот ответ, который вам нужен, он может помочь людям, заинтересованным в этом вопросе "ключ/значение".

Ответ 5

function getIndexByAttribute(list, attr, val){
    var result = null;
    $.each(list, function(index, item){
        if(item[attr].toString() == val.toString()){
           result = index;
           return false;     // breaks the $.each() loop
        }
    });
    return result;
}

Ответ 6

Сделайте так: -

var peoples = [
  { "name": "bob", "dinner": "pizza" },
  { "name": "john", "dinner": "sushi" },
  { "name": "larry", "dinner": "hummus" }
];

$.each(peoples, function(i, val) {
    $.each(val, function(key, name) {
        if (name === "john")
            alert(key + " : " + name);
    });
});

ВЫВОД:

name : john

Обратитесь LIVE DEMO

Ответ 7

Вы также можете сделать его методом многократного использования, добавив JavaScript:

Array.prototype.findIndexBy = function(key, value) {
    return this.findIndex(item => item[key] === value)
}

const peoples = [{name: 'john'}]
const cats = [{id: 1, name: 'kitty'}]

peoples.findIndexBy('name', 'john')
cats.findIndexBy('id', 1)