如何将List<String>转换为Dictionary<int,String>?

29

我有一个List<String>,我需要将它转换为具有自动生成键的Dictionary<int,String>,是否有更短的方法来完成?我已经尝试了:

    var dictionary = new Dictionary<int, String>();
    int index = 0;
    list.ForEach(x=>{
      definitions.Add(index, x);
      index++;
});

但我认为这是不道德的做法。

4个回答

77
var dict = list.Select((s, i) => new { s, i }).ToDictionary(x => x.i, x => x.s);

这将从0开始键入;如果我想从任何其他数字开始,比如10,并且每次增加10而不是1,该怎么办? - zak
@zak,当你使用了SkipWhere后得到了什么? - L.B
如果列表中有重复的键,我只想忽略添加重复项到字典中,该怎么办? - Rod
1
略微变化,使用未命名元组(C# 7): var dict = list.Select((s, i) => (s, i)).ToDictionary(x => x.i, x => x.s); - Jan Van Overbeke

18

我觉得这是最整洁的。

int index = 0;
var dictionary = myList.ToDictionary(item => index++);

1
这比被接受的答案简单多了 - 为什么要把它变得如此复杂才能将其放入一行中呢? - jbyrd

6

我认为你所写的比LINQ更易读(并且作为额外优势,更加高效):

foreach(var item in list)
    dictionary[index++] = item;

在使用赋值运算符时,例如dictionary[index++] = item;,存在一个隐藏的陷阱:现有的键将被静默覆盖!当使用Add方法时,它会抛出一个异常,指示键已经存在,并在运行时以某种方式通知程序员。这总是取决于用例 ;) 通常情况下。 - Mong Zhu
2
@MongZhu 我不会称它为隐藏或静默。当我们说 dict[key1] = value1 时,如果 key1 已经存在,则该元素将被覆盖。如果不存在,则会创建一个新元素。这就是字典的正常工作方式,并且已经有文档进行了说明。在这种情况下,字典是一个新的空实例,因此没有现有的键。 - Eren Ersönmez
我知道这已经有文档记录了。在我的同事掉进这个陷阱后,我们才去阅读文档;但是只是在那之后 :D “字典是一个新的空实例,因此不存在任何现有的键”,是的,这就是我所说的根据用例而定。在这种情况下,这是一个非常有效的方法。 - Mong Zhu
1
@MongZhu 你说得对,有些东西被记录并不意味着它很明显。我想我们只能在这里留下文档链接(上面),希望能帮助其他人 :) - Eren Ersönmez

4

使用:

var dict = list.Select((x, i) => new {x, i})
    .ToDictionary(a => a.i, a => a.x);

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接