将2个Linq序列合并为一个,优先级

时间:2009-06-17 21:04:43

标签: linq

我有2个序列,每个序列返回一个带有2个字段的匿名类型(称为x和y)。从语义上讲,x在这两个序列中都作为键和y值。

如果两个中出现相同的x,那么如何指定第一个序列优先于第二个序列,从而将它们合并为1个序列?

2 个答案:

答案 0 :(得分:1)

如果没有Linq,你可能会发现它更容易,但我在想这样的事情:

var distinctWithPrecedence = seq1
  .Concat(seq2)
  .GroupBy(i => i.x)
  .Select(g => g.First());

如果Linq没有做太多的事情。基本思想是按键分组。然后通过分组从每个元素中拉出第一个元素。如果Linq表现我认为它应该是第一个元素将是连接列表中的第一个元素,这意味着第一个序列具有先例。

可能有其他方法可以做到这一点,但这是第一个浮现在脑海中的方法。

答案 1 :(得分:1)

我会从

开始
var res = seq1.Union(seq2, Comparer);

但是Enumerable.Union的文档没有指定匹配元素从哪个序列中获取,并且需要Comparer作为IEqualityComparer<TSource>的实现,如果{TSource则不会{1}}是一种匿名类型(但可能值得具体来允许这样做。)

否则你需要实现自己的助手,例如:

IEnumerable<KeyValuePair<TKey, TValue>> Union(
                     this IEnumerable<KeyValuePair<TKey, TValue>> first,
                     IEnumerable<KeyValuePair<TKey, TValue>> second) {
   var allFirst = first.ToDictionary(v => v.Key, v => v.Value);
   foreach (var kv in allFirst) { yield return kv; }

   foreach (var s in second) {
     if (!allFirst.ContainsKey(s.Key)) {
       yield return s;
     }
 }

(如果你想坚持自己的类型(属性x&amp; y),你可以在单个类型参数上创建这个泛型,但是你需要添加一个类型约束来访问单独的属性。)