Как получить ключ в объекте JavaScript по его значению? - PullRequest
283 голосов
/ 28 марта 2012

У меня есть довольно простой объект JavaScript, который я использую в качестве ассоциативного массива. Существует ли простая функция, позволяющая мне получить ключ для значения, или мне нужно выполнить итерацию объекта и найти его вручную?

Ответы [ 23 ]

9 голосов
/ 22 апреля 2014

Я создал библиотеку bimap (https://github.com/alethes/bimap), которая реализует мощный, гибкий и эффективный интерфейс двунаправленной карты JavaScript. Он не имеет зависимостей и может использоваться как на стороне сервера (в Node .js, вы можете установить его с npm install bimap) и в браузере (со ссылкой на lib / bimap.js ).

Основные операции действительно просты:

var bimap = new BiMap;
bimap.push("k", "v");
bimap.key("k") // => "v"
bimap.val("v") // => "k"

bimap.push("UK", ["London", "Manchester"]);
bimap.key("UK"); // => ["London", "Manchester"]
bimap.val("London"); // => "UK"
bimap.val("Manchester"); // => "UK"

Получение сопоставления ключ-значение одинаково быстро в обоих направлениях. Под капотом нет дорогостоящих обходов объектов / массивов, поэтому среднее время доступа остается постоянным независимо от размера данных.

3 голосов
/ 20 августа 2013

Поскольку значения уникальны, должна быть возможность добавить значения в качестве дополнительного набора ключей. Это можно сделать с помощью следующего ярлыка.

var foo = {};
foo[foo.apple = "an apple"] = "apple";
foo[foo.pear = "a pear"] = "pear";

Это позволит получить либо ключ, либо значение:

var key = "apple";
var value = "an apple";

console.log(foo[value]); // "apple"
console.log(foo[key]); // "an apple"

Предполагается, что между ключами и значениями нет общих элементов.

2 голосов
/ 28 апреля 2016

Как будто этот вопрос не был избит до полусмерти ...

Вот один только для любопытства, которое он вам приносит ...

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

var o = { a: '_A', b: '_B', c: '_C' }
  , json = JSON.stringify(o)
  , split = json.split('')
  , nosj = split.reverse()
  , o2 = nosj.join('');

var reversed = o2.replace(/[{}]+/g, function ($1) { return ({ '{':'}', '}':'{' })[$1]; })
  , object = JSON.parse(reversed)
  , value = '_B'
  , eulav = value.split('').reverse().join('');

console.log('>>', object[eulav]);

Может быть, здесь есть что-то полезное, что можно извлечь из этого ...

Надеюсь, это вас забавляет.1010 *

2 голосов
/ 28 марта 2013

Или еще проще - создайте новый объект с ключами и значениями в нужном вам порядке, а затем посмотрите на этот объект.У нас были конфликты с использованием прототипов кодов выше.Вам не нужно использовать функцию String вокруг клавиши, которая является необязательной.

 newLookUpObj = {};
 $.each(oldLookUpObj,function(key,value){
        newLookUpObj[value] = String(key);
    });
1 голос
/ 04 июня 2015

Обычно я рекомендую lodash, а не подчеркивание.

Если он у вас есть, используйте его.

Если у вас его нет, вам следует рассмотреть возможность использования пакета lodash.invert npm, которыйдовольно крошечный.

Вот как вы можете проверить это с помощью gulp:

1) Создайте файл с именем gulpfile.js со следующим содержимым:

// Filename: gulpfile.js
var gulp = require('gulp');
var invert = require('lodash.invert');   
gulp.task('test-invert', function () {
  var hash = {
    foo: 1,
    bar: 2
  };
  var val = 1;
  var key = (invert(hash))[val];  // << Here's where we call invert!
  console.log('key for val(' + val + '):', key);
});

2)Установите пакет lodash.invert и проглотите

$ npm i --save lodash.invert && npm install gulp

3) Проверьте, что он работает:

$ gulp test-invert
[17:17:23] Using gulpfile ~/dev/npm/lodash-invert/gulpfile.js
[17:17:23] Starting 'test-invert'...
key for val(1): foo
[17:17:23] Finished 'test-invert' after 511 μs

Ссылки

https://www.npmjs.com/package/lodash.invert

https://lodash.com/

Различия между подчеркиванием и подчеркиванием

https://github.com/gulpjs/gulp

1 голос
/ 28 сентября 2017

Вот решение Lodash, которое работает для объекта с плоским ключом => значение, а не для вложенного объекта. Предложение принятого ответа использовать _.findKey работает для объектов с вложенными объектами, но не работает в этом обычном случае.

Этот подход инвертирует объект, меняя ключи значениями, а затем находит ключ, просматривая значение нового (инвертированного) объекта. Если ключ не найден, то возвращается false, который я предпочитаю, чем undefined, но вы можете легко поменять его в третьем параметре метода _.get в getKey().

// Get an object's key by value
var getKey = function( obj, value ) {
	var inverse = _.invert( obj );
	return _.get( inverse, value, false );
};

// US states used as an example
var states = {
	"AL": "Alabama",
	"AK": "Alaska",
	"AS": "American Samoa",
	"AZ": "Arizona",
	"AR": "Arkansas",
	"CA": "California",
	"CO": "Colorado",
	"CT": "Connecticut",
	"DE": "Delaware",
	"DC": "District Of Columbia",
	"FM": "Federated States Of Micronesia",
	"FL": "Florida",
	"GA": "Georgia",
	"GU": "Guam",
	"HI": "Hawaii",
	"ID": "Idaho",
	"IL": "Illinois",
	"IN": "Indiana",
	"IA": "Iowa",
	"KS": "Kansas",
	"KY": "Kentucky",
	"LA": "Louisiana",
	"ME": "Maine",
	"MH": "Marshall Islands",
	"MD": "Maryland",
	"MA": "Massachusetts",
	"MI": "Michigan",
	"MN": "Minnesota",
	"MS": "Mississippi",
	"MO": "Missouri",
	"MT": "Montana",
	"NE": "Nebraska",
	"NV": "Nevada",
	"NH": "New Hampshire",
	"NJ": "New Jersey",
	"NM": "New Mexico",
	"NY": "New York",
	"NC": "North Carolina",
	"ND": "North Dakota",
	"MP": "Northern Mariana Islands",
	"OH": "Ohio",
	"OK": "Oklahoma",
	"OR": "Oregon",
	"PW": "Palau",
	"PA": "Pennsylvania",
	"PR": "Puerto Rico",
	"RI": "Rhode Island",
	"SC": "South Carolina",
	"SD": "South Dakota",
	"TN": "Tennessee",
	"TX": "Texas",
	"UT": "Utah",
	"VT": "Vermont",
	"VI": "Virgin Islands",
	"VA": "Virginia",
	"WA": "Washington",
	"WV": "West Virginia",
	"WI": "Wisconsin",
	"WY": "Wyoming"
};

console.log( 'The key for "Massachusetts" is "' + getKey( states, 'Massachusetts' ) + '"' );
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.4/lodash.min.js"></script>
1 голос
/ 27 января 2014

Это небольшое расширение метода Underscorejs, и вместо него используется Lodash :

var getKeyByValue = function(searchValue) {
  return _.findKey(hash, function(hashValue) {
    return searchValue === hashValue;
  });
}

FindKey будет найдите и верните первый ключ , который соответствует значению.
Если вместо этого требуется последнее совпадение, используйте FindLastKey .

1 голос
/ 26 января 2013

http://jsfiddle.net/rTazZ/2/

var a = new Array(); 
    a.push({"1": "apple", "2": "banana"}); 
    a.push({"3": "coconut", "4": "mango"});

    GetIndexByValue(a, "coconut");

    function GetIndexByValue(arrayName, value) {  
    var keyName = "";
    var index = -1;
    for (var i = 0; i < arrayName.length; i++) { 
       var obj = arrayName[i]; 
            for (var key in obj) {          
                if (obj[key] == value) { 
                    keyName = key; 
                    index = i;
                } 
            } 
        }
        //console.log(index); 
        return index;
    } 
1 голос
/ 05 октября 2018

Вот мое решение первым:

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

function findKey(object, value) {

    for (let key in object)
        if (object[key] === value) return key;

    return "key is not found";
}

const object = { id_1: "apple", id_2: "pear", id_3: "peach" };

console.log(findKey(object, "pear"));
//expected output: id_2

Мы можем просто написать findKey (массив, значение), который принимает два параметра, которые являются объектом и значением ключа, который вы ищете. Таким образом, этот метод можно использовать повторно, и вам не нужно каждый раз вручную повторять объект, передавая только два параметра для этой функции.

1 голос
/ 02 июля 2015

Дано input={"a":"x", "b":"y", "c":"x"} ...

Чтобы использовать первое значение (например, output={"x":"a","y":"b"}): output=Object.keys(input).reduceRight(function(accum,key,i){accum[input[key]]=key;return accum;},{})

Чтобы использовать последнее значение (например, output={"x":"c","y":"b"}): output=Object.keys(input).reduce(function(accum,key,i){accum[input[key]]=key;return accum;},{})

Чтобы получить массив ключей для каждого значения (например, output={"x":["c","a"],"y":["b"]}): output=Object.keys(input).reduceRight(function(accum,key,i){accum[input[key]]=(accum[input[key]]||[]).concat(key);return accum;},{})

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...