I happened to have seen some code where this guy passed a lambda expression to a ArrayList.Sort(IComparer here) or a IEnumerable.SequenceEqual(IEnumerable list, IEqualityCom
I was also googling the web for a solution, but i didn't found any satisfying one. So i've created a generic EqualityComparerFactory:
using System;
using System.Collections.Generic;
///
/// Utility class for creating instances
/// from Lambda expressions.
///
public static class EqualityComparerFactory
{
/// Creates the specified .
/// The type to compare.
/// The get hash code delegate.
/// The equals delegate.
/// An instance of .
public static IEqualityComparer Create(
Func getHashCode,
Func equals)
{
if (getHashCode == null)
{
throw new ArgumentNullException(nameof(getHashCode));
}
if (equals == null)
{
throw new ArgumentNullException(nameof(equals));
}
return new Comparer(getHashCode, equals);
}
private class Comparer : IEqualityComparer
{
private readonly Func _getHashCode;
private readonly Func _equals;
public Comparer(Func getHashCode, Func equals)
{
_getHashCode = getHashCode;
_equals = equals;
}
public bool Equals(T x, T y) => _equals(x, y);
public int GetHashCode(T obj) => _getHashCode(obj);
}
}
The idea is, that the CreateComparer method takes two arguments: a delegate to GetHashCode(T) and a delegate to Equals(T,T)
Example:
class Person
{
public int Id { get; set; }
public string LastName { get; set; }
public string FirstName { get; set; }
}
class Program
{
static void Main(string[] args)
{
var list1 = new List(new[]{
new Person { Id = 1, FirstName = "Walter", LastName = "White" },
new Person { Id = 2, FirstName = "Jesse", LastName = "Pinkman" },
new Person { Id = 3, FirstName = "Skyler", LastName = "White" },
new Person { Id = 4, FirstName = "Hank", LastName = "Schrader" },
});
var list2 = new List(new[]{
new Person { Id = 1, FirstName = "Walter", LastName = "White" },
new Person { Id = 4, FirstName = "Hank", LastName = "Schrader" },
});
// We're comparing based on the Id property
var comparer = EqualityComparerFactory.Create(
a => a.Id.GetHashCode(),
(a, b) => a.Id==b.Id);
var intersection = list1.Intersect(list2, comparer).ToList();
}
}