Словарь с несколькими записями с одним и тем же ключом
Мне нужен словарь как объект, который может хранить несколько записей с одним и тем же ключом. Является ли это доступным как стандартная коллекция, или мне нужно сворачивать самостоятельно?
Чтобы уточнить, я хочу иметь возможность сделать что-то вроде этого:
var dict = new Dictionary<int, String>();
dict.Add(1, "first");
dict.Add(1, "second");
foreach(string x in dict[1])
{
Console.WriteLine(x);
}
Вывод:
first
second
Ответы
Ответ 1
В .NET 3.5 вы можете использовать Lookup вместо словаря.
var items = new List<KeyValuePair<int, String>>();
items.Add(new KeyValuePair<int, String>(1, "first"));
items.Add(new KeyValuePair<int, String>(1, "second"));
var lookup = items.ToLookup(kvp => kvp.Key, kvp => kvp.Value);
foreach (string x in lookup[1])
{
Console.WriteLine(x);
}
Класс Lookup
является неизменным. Если вы хотите изменить версию, вы можете использовать EditableLookup
из MiscUtil.
Ответ 2
Я бы рекомендовал сделать что-то вроде этого:
var dict = new Dictionary<int, HashSet<string>>();
dict.Add(1, new HashSet<string>() { "first", "second" });
Ответ 3
Dictionary<T,K>
не поддерживает такое поведение, и в библиотеке базового класса нет такого набора данных, обеспечивающего такое поведение. Самый простой способ - построить составную структуру данных следующим образом:
var data = new Dictionary<int, List<string>>();
В качестве второго параметра вы должны использовать коллекцию, которая обеспечивает качества, которые вы ищете, т.е. стабильный порядок ⇒ List<T>
, быстрый доступ HashSet<T>
и т.д.
Ответ 4
Вы определенно хотите использовать NameValueCollection:
используя System.Collections.Specialized;
NameValueCollection nvc = new NameValueCollection();
nvc.Add("pets", "Dog");
nvc.Add("pets", "Rabbit");
Console.WriteLine(nvc["pets"]);
//returns Dog,Rabbit
Ответ 5
То, что вы ищете, на самом деле не является Словарем в традиционном смысле (см. Ассоциативный массив).
Нет класса, насколько мне известно, который предлагает это в рамках (System.Linq.Lookup
не предоставляет конструктор), но вы можете создать класс самостоятельно, который реализует ILookup<TKey, TElement>
Ответ 6
Возможно, вы можете использовать словарь на своем основном ключе, в котором каждый элемент является списком или другой коллекцией вашего вторичного ключа. Чтобы добавить элемент в свою структуру данных, проверьте, существует ли первичный ключ. Если нет, создайте новый список отдельных элементов со своим значением и сохраните его в словаре. Если первичный ключ существует, добавьте свое значение в список, который находится в словаре.