2011-12-21 1 views
3

У меня есть 3 раскрывающихся списка на моей странице, параметры в третьем раскрывающемся списке зависят от выбора в первых двух выпадающих списках.Карту Javascript с двумя значениями в ключе

Так что мне интересно, есть ли способ реализовать карту в javaScript с двумерным ключом? Мне нравится <Key1, Key2> -> Value.

Я думаю, что простой способ состоит в том, чтобы объединить два ключа в одну строку. Есть ли способ, который более приличный?

Спасибо.

+2

Если у вас есть ключи как строки и вы можете убедиться, что они не содержат конкретных символов, таких как '|', вы можете использовать что-то вроде 'map [a + '|' + b] ' – zzzzBov

ответ

5

Вы можете иметь объект, который содержит несколько объектов:

var options = { 
    'option 1': { 
     'option 1.1': [ 
      'option 1.1.1', 
      'option 1.1.2', 
      'option 1.1.3', 
      'option 1.1.4' 
     ], 
     'option 1.2': [ 
      'option 1.2.1', 
      /* etc. */ 
}; 

Затем вы сможете получить доступ к опции для третьего выпадающего списка, как options[firstSelectedValue][secondSelectedValue].


EDIT: Here's a demo, too, используя некоторые новые функции, которые могут потребоваться для реализации, если вы просматриваете с помощью Internet Explorer 8 или ниже :)

1

Что с конкатенации двух ключей? Все, что вам нужно, это убедиться, что конкатенированные ключи уникальны, и я думаю, что этого легко добиться, разделив два значения символом, который не используется ни одним из двух ключей.

0

Другого выхода нет. JS-карта - простой объект, поэтому ключ такой же, как имя свойства. Даже если вы попытаетесь использовать, например. массив как ключ, он будет преобразован в строку. Вы должны выполнить эту строку с некоторым специальным символом между или хранить значения в массиве и сканировать его при каждом доступе.

2

Вы можете установить ключ в виде массива. Просто создайте свой массив [key1, key2];

Затем установите его в качестве ключа и связать его с вашим значением

OBJ [[key1, key2]] = "мое значение";

Вот jsFiddle

http://jsfiddle.net/TwQLW/

+1

Свойства объекта * должны * быть строками, поэтому любые другие переданные значения преобразуются в строку. Это делает этот ответ таким же, как объединение двух строк, потому что массивы автоматически соединяются с ','. –

+0

Спасибо @ Keith.Abramo. –

0

Я создал общую структуру данных для этой цели, как у меня была аналогичная проблема:

https://github.com/vikashmadhow/map

Я знаю довольно много времени прошло с тех пор этот вопрос был задан; надеюсь, это может помочь другим.

0

Я искал аналогичную структуру данных, но не смог найти. Я работал с TypeScript, поэтому я разработал решение с использованием TypeScript.

export class TwoMapKey<T> { 
    private __map__: object; 

    constructor() { 
     this.__map__ = new Object(); 
     this.get = this.get.bind(this); 
     this.set = this.set.bind(this); 
     this.remove = this.remove.bind(this); 
     this.keys = this.keys.bind(this); 
     this.nestedKeys = this.nestedKeys.bind(this); 
     this.clear = this.clear.bind(this); 
    } 

    public get(key: string, nestedKey: string): T { 
     if (!this.__map__[key] || this.__map__[key] && !this.__map__[key][nestedKey]) 
      return; 

     return this.__map__[key][nestedKey]; 
    } 

    public set(key: string, nestedKey: string, value: T): void { 
     if (!this.__map__[key]) { 
      this.__map__[key] = new Object(); 
     } 

     Object.defineProperty(this.__map__[key], nestedKey, { value: value, configurable: true, enumerable: true }); 
    } 

    public remove(key, nestedKey): void { 
     if (!this.__map__[key]) { 
      return; 
     } 

     delete this.__map__[key][nestedKey]; 
    } 

    public keys(): string[] { 
     return Object.getOwnPropertyNames(this.__map__); 
    } 

    public nestedKeys(): Array<string[]> { 
     return Object.getOwnPropertyNames(this.__map__).map(key => Object.keys(this.__map__[key])); 
    } 

    public clear(): void { 
     Object.getOwnPropertyNames(this.__map__).forEach(property => { 
      delete this.__map__[property]; 
     }); 
    } } 

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

let twoKeyMap = new TwoKeyMap<any>(); 
twoKeyMap.set('mainKey1', 'nestedKey1', {value: 'value'}); 

его не так ЭФФЕКТИВНАЯ как HashMap. Вы должны иметь возможность конвертировать то же самое в ES6 или ES5 легко.

Смежные вопросы