I am playing with LINQ to learn about it, but I can\'t figure out how to use Distinct
when I do not have a simple list (a simple list of integers is pretty easy
When we faced such a task in our project we defined a small API to compose comparators.
So, the use case was like this:
var wordComparer = KeyEqualityComparer.Null().
ThenBy(item => item.Text).
ThenBy(item => item.LangID);
...
source.Select(...).Distinct(wordComparer);
And API itself looks like this:
using System;
using System.Collections;
using System.Collections.Generic;
public static class KeyEqualityComparer
{
public static IEqualityComparer Null()
{
return null;
}
public static IEqualityComparer EqualityComparerBy(
this IEnumerable source,
Func keyFunc)
{
return new KeyEqualityComparer(keyFunc);
}
public static KeyEqualityComparer ThenBy(
this IEqualityComparer equalityComparer,
Func keyFunc)
{
return new KeyEqualityComparer(keyFunc, equalityComparer);
}
}
public struct KeyEqualityComparer: IEqualityComparer
{
public KeyEqualityComparer(
Func keyFunc,
IEqualityComparer equalityComparer = null)
{
KeyFunc = keyFunc;
EqualityComparer = equalityComparer;
}
public bool Equals(T x, T y)
{
return ((EqualityComparer == null) || EqualityComparer.Equals(x, y)) &&
EqualityComparer.Default.Equals(KeyFunc(x), KeyFunc(y));
}
public int GetHashCode(T obj)
{
var hash = EqualityComparer.Default.GetHashCode(KeyFunc(obj));
if (EqualityComparer != null)
{
var hash2 = EqualityComparer.GetHashCode(obj);
hash ^= (hash2 << 5) + hash2;
}
return hash;
}
public readonly Func KeyFunc;
public readonly IEqualityComparer EqualityComparer;
}
More details is on our site: IEqualityComparer in LINQ.