LINQ:元组列表转换为列表元组

11
4个回答

12

使用单个LINQ调用不可能实现,但是您可以轻松地使用代码完成:

Tuple<List<A>, List<B>> Unpack<A, B>(List<Tuple<A, B>> list)
{
  var listA = new List<A>(list.Count);
  var listB = new List<B>(list.Count);
  foreach (var t in list)
  {
    listA.Add(t.Item1);
    listB.Add(t.Item2);
  }

  return Tuple.Create(listA, listB);
}

3
这可能是最简单的方法,而不需要对列表进行两次枚举。 - vcsjones
4
是的,你没有不断调整内部缓冲区的大小。 - Servy
1
@Aducci 一个列表有一个内部缓冲区,最多可以容纳N个元素。当你添加更多元素并且缓冲区变得太小时,将创建一个新的缓冲区,将所有元素复制过去并使用新的缓冲区 - 这是一个缓慢的过程。当你知道元素的数量时,你可以告诉列表“嘿,我希望你最初分配足够的内存来容纳N个元素”,这样就不需要任何新的分配了。 - Martin1921
1
代码可以写得更简洁,但本质上是相同的:`var unpacked = new Tuple<List<int>, List<string>>(new List<int>(pairs.Count), new List<string>(pairs.Count)); pairs.ForEach(pair => { unpacked.Item1.Add(pair.Item1); unpacked.Item2.Add(pair.Item2); });` - Adam Houldsworth
3
这样你就不得不再次枚举列表,而我想要避免这种情况。 - Martin1921
显示剩余6条评论

6
你可以使用 聚合
Tuple<List<A>, List<B>> Unpack<A, B>(List<Tuple<A, B>> list)
{
    return list.Aggregate(Tuple.Create(new List<A>(list.Count), new List<B>(list.Count)),
                          (unpacked, tuple) =>
                          {
                              unpacked.Item1.Add(tuple.Item1);
                              unpacked.Item2.Add(tuple.Item2);
                              return unpacked;
                          });
}

2
Tuple<List<A>, List<B>> Unpack<A, B>(List<Tuple<A, B>> list) {
            return Tuple.Create(list.Select(e => e.Item1).ToList(),list.Select(e => e.Item2).ToList());
}

-2
public Tuple<List<int>,List<int>> Convert(List<Tuple<int, int>> BaseList)
{
    return new Tuple<List<int>,List<int>>((from tuple in BaseList
                                                        select tuple.Item1).ToList(),
                                                        (from tuple in BaseList
                                                        select tuple.Item2).ToList());
}

我认为这是一个整数列表


然后他可以将“int”替换为“object”。 - Y2theZ
4
不,他不应该这样做。这种方法应该是通用的,因此它仍然具有强类型但可以使用任意类型。 - Servy

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