Let's say I have a List<NameValuePair>
, where NameValuePair is a simple object that has a Name property and a Value property, both strings.
假设我有一个List
The list is populated with values like this:
列表中填充了以下值:
name = "name1", value = "value1"
name = "name1", value = "value2"
name = "name2", value = "value3"
name = "name3", value = "value4"
Note that there are two instances of the "name1" key. There can be any number of keys (since this is a List).
请注意,“name1”键有两个实例。可以有任意数量的键(因为这是一个列表)。
I want to turn this List into a new list, which has just unique keys, and groups any values with the same key name as an array/list of that key.
我想将此List转换为一个新列表,该列表只包含唯一键,并将具有相同键名的任何值分组为该键的数组/列表。
So the above should become:
所以上面应该成为:
name = "name1", value = "value1", "value2" // value is a string array or list
name = "name2", value = "value3"
name = "name3", value = "value4"
What is the easiest way to accomplish this?
实现这一目标的最简单方法是什么?
5 个解决方案
#1
Maybe with a Dictionary<string,List<string>> you could do something like
也许使用Dictionary
for (var kv in mylistofnamed) {
if (!dict.ContainsKey(kv.Key))
dict[kv.Key] = new List<string>();
dict[kv.Key].Add(kv.Value);
}
?
#2
The easiest way is with a ILookup, which is essentially like a dictionary but can have more than one value for each key.
最简单的方法是使用ILookup,它基本上类似于字典,但每个键可以有多个值。
You can do something like this to create your lookup:
您可以执行以下操作来创建查找:
var lookup = list.ToLookup(pair => pair.name,
pair => pair.value);
Then you could print the name/value pairs like this:
然后你可以像这样打印名称/值对:
foreach (var nameGroup in lookup)
{
var name = nameGroup.Key;
foreach (string value in nameGroup)
Console.WriteLine("Name: {0}, Value: {1}", name, value);
}
#3
If you only need a read-only collection then Lookup
will do the trick, as in Meta-Knight's answer.
如果你只需要一个只读集合,那么Lookup就可以解决这个问题,就像Meta-Knight的回答一样。
If you need to modify the collection after its initial creation/population, then you probably need something like Dictionary<string, List<string>>
. You can create and populate such a dictionary from your original list using LINQ:
如果你需要在初始创建/填充后修改集合,那么你可能需要像Dictionary
var dict = list
.GroupBy(x => x.Name)
.ToDictionary(x => x.Key, y => y.Select(z => z.Value).ToList());
#4
One way is with a dictionary:
一种方法是使用字典:
http://arcanecode.com/2007/03/05/dictionaries-in-c-the-hashtable/
A HashTable can do what you need with unique keys. You will have to supply a List as the value however, since you will be storing multiple values per key.
HashTable可以使用唯一键执行您所需的操作。但是,您必须提供List作为值,因为您将为每个键存储多个值。
Here's another easy example:
这是另一个简单的例子:
http://dotnetperls.com/hashtable-keys
You will need to iterate over each KeyValuePair in your list to populate the HashTable by storing the name as the key and the values as the value. Because you may have a name that points to multiple values, you will need your values in the HashTable to be Lists.
您需要遍历列表中的每个KeyValuePair,以通过将名称存储为键并将值存储为值来填充HashTable。因为您可能有一个指向多个值的名称,所以您需要将HashTable中的值作为列表。
Check for the existence of the name in the HashTable, if it's not there, create a new list for that name and add the value to the list. If the key already exists, access that element in the HashTable and add the new value to the list that maps to the key.
检查HashTable中是否存在名称,如果不存在,则为该名称创建一个新列表并将值添加到列表中。如果密钥已存在,则访问HashTable中的该元素,并将新值添加到映射到密钥的列表中。
#5
All classes that implement the IDictionary
interface or the Generic IDictionary Interface enforce uniqueness checks for the Keys. You could use any of the classes, though I confess my preference for the Generic Dictionary<TKey, TValue>
class.
实现IDictionary接口或通用IDictionary接口的所有类都强制执行Keys的唯一性检查。您可以使用任何类,但我承认我对Generic Dictionary
When adding values, you can just check if the Dictionary object already contains the supplied Key. If not, then you can add the item into the Dictionary.
添加值时,您只需检查Dictionary对象是否已包含提供的Key。如果没有,则可以将该项添加到词典中。
#1
Maybe with a Dictionary<string,List<string>> you could do something like
也许使用Dictionary
for (var kv in mylistofnamed) {
if (!dict.ContainsKey(kv.Key))
dict[kv.Key] = new List<string>();
dict[kv.Key].Add(kv.Value);
}
?
#2
The easiest way is with a ILookup, which is essentially like a dictionary but can have more than one value for each key.
最简单的方法是使用ILookup,它基本上类似于字典,但每个键可以有多个值。
You can do something like this to create your lookup:
您可以执行以下操作来创建查找:
var lookup = list.ToLookup(pair => pair.name,
pair => pair.value);
Then you could print the name/value pairs like this:
然后你可以像这样打印名称/值对:
foreach (var nameGroup in lookup)
{
var name = nameGroup.Key;
foreach (string value in nameGroup)
Console.WriteLine("Name: {0}, Value: {1}", name, value);
}
#3
If you only need a read-only collection then Lookup
will do the trick, as in Meta-Knight's answer.
如果你只需要一个只读集合,那么Lookup就可以解决这个问题,就像Meta-Knight的回答一样。
If you need to modify the collection after its initial creation/population, then you probably need something like Dictionary<string, List<string>>
. You can create and populate such a dictionary from your original list using LINQ:
如果你需要在初始创建/填充后修改集合,那么你可能需要像Dictionary
var dict = list
.GroupBy(x => x.Name)
.ToDictionary(x => x.Key, y => y.Select(z => z.Value).ToList());
#4
One way is with a dictionary:
一种方法是使用字典:
http://arcanecode.com/2007/03/05/dictionaries-in-c-the-hashtable/
A HashTable can do what you need with unique keys. You will have to supply a List as the value however, since you will be storing multiple values per key.
HashTable可以使用唯一键执行您所需的操作。但是,您必须提供List作为值,因为您将为每个键存储多个值。
Here's another easy example:
这是另一个简单的例子:
http://dotnetperls.com/hashtable-keys
You will need to iterate over each KeyValuePair in your list to populate the HashTable by storing the name as the key and the values as the value. Because you may have a name that points to multiple values, you will need your values in the HashTable to be Lists.
您需要遍历列表中的每个KeyValuePair,以通过将名称存储为键并将值存储为值来填充HashTable。因为您可能有一个指向多个值的名称,所以您需要将HashTable中的值作为列表。
Check for the existence of the name in the HashTable, if it's not there, create a new list for that name and add the value to the list. If the key already exists, access that element in the HashTable and add the new value to the list that maps to the key.
检查HashTable中是否存在名称,如果不存在,则为该名称创建一个新列表并将值添加到列表中。如果密钥已存在,则访问HashTable中的该元素,并将新值添加到映射到密钥的列表中。
#5
All classes that implement the IDictionary
interface or the Generic IDictionary Interface enforce uniqueness checks for the Keys. You could use any of the classes, though I confess my preference for the Generic Dictionary<TKey, TValue>
class.
实现IDictionary接口或通用IDictionary接口的所有类都强制执行Keys的唯一性检查。您可以使用任何类,但我承认我对Generic Dictionary
When adding values, you can just check if the Dictionary object already contains the supplied Key. If not, then you can add the item into the Dictionary.
添加值时,您只需检查Dictionary对象是否已包含提供的Key。如果没有,则可以将该项添加到词典中。