通过值比较两个字典的条目,然后返回它们各自的键?

时间:2019-12-03 20:45:47

标签: c# linq dictionary intersect

我有2个类型为Dictionary<int, (int, int)>的字典,第一个int是它们的关键字,(int, int)是它们的值。

使用var intersections = dict1.Values.Intersect(dict2.Values);,我可以比较值并返回一个IEnumerable,该值是介于两者之间的所有值,但是这并没有给我键。并且使用var intersections = dict1.Keys.Intersect(dict2.Keys);将返回出现在两个字典中的键,这是...每个键,因为键只是从1开始并为每个条目加1,所以它是无用的。

我想按条目的值比较条目,然后访问它们的键。因此,例如,如果条目(12、36)出现在dict1的键20和dict2的键45处,我想有一种访问20和45的方法。

我完全不知所措。我能够比较值和返回值,我能够比较键和返回键,但是我无法比较值和返回键。怎么办?

谢谢!

3 个答案:

答案 0 :(得分:1)

dict1.Union(dict2)
    .GroupBy(kvp => kvp.Value)
    .Where(g => g.Count() > 1) // but this doesn't account for equal values in same dictionary if that's important
    .Select(g => new
    {
        Value = g.Key,
        Keys = g.Select(kvp => kvp.Key),
    });

或者,您可以加入每个字典的Value对象的KeyValuePair<TKey,TValue>属性。

答案 1 :(得分:0)

您可以创建自己的IEqualityComparer并使用要求它的Intersect重载。

static void Main(string[] args)
{
    var dict1 = new Dictionary<int, (int, int)>();
    dict1.Add(1, (1, 1));
    dict1.Add(2, (2, 2));
    dict1.Add(3, (3, 3));
    var dict2 = new Dictionary<int, (int, int)>();
    dict2.Add(4, (2, 2));
    dict2.Add(5, (3, 3));
    dict2.Add(6, (4, 4));

    var intersection = dict1.Intersect(dict2, new eq());

    foreach (var i in intersection)
        Console.WriteLine($"Key: {i.Key}, Value: {i.Value}");
    Console.ReadLine();
}

class eq : IEqualityComparer<KeyValuePair<int, (int, int)>>
{
    public bool Equals(KeyValuePair<int, (int, int)> x, KeyValuePair<int, (int, int)> y)
    {
        return x.Value == y.Value;
    }

    public int GetHashCode(KeyValuePair<int, (int, int)> obj)
    {
        unchecked
        {
            int hash = 17;
            hash = hash * 23 + obj.Value.Item1;
            hash = hash * 23 + obj.Value.Item2;
            return hash;
        }
    }
}
  

键:2,值:(2,2)
  键:3,值:(3,3)

Jon Skeet的this answer中的哈希

答案 2 :(得分:0)

您可以简单地使用Where过滤器并检查其他词典是否包含值:

var matches = dict1.Where(d => dict2.ContainsValue(d.Value));

这将返回一个枚举,然后您可以根据需要使用ToDictionary()ToList()

编辑:

使用此Union返回比赛的双方:

dict1.Where(d => dict2.ContainsValue(d.Value))
     .Union(dict2.Where(d => dict1.ContainsValue(d.Value)));

HTH