Motivation
I'm looking to implement IComparer<>
in a similar way to the demo code below. Where Foo
is the type of objects I need to compare. It does not implement IComparable
, but I'm providing an IComparer
class for each field so the user can elect to equate to instances based on one field value.
enum Day {Sat, Sun, Mon, Tue, Wed, Thu, Fri};
class Foo {
public int Bar;
public string Name;
public Day Day;
}
Comparer classes are:
// Compares all fields in Foo
public class FooComparer : IEqualityComparer<Foo>
{
public bool Equals(Foo x, Foo y)
{
if (ReferenceEquals(x, y)) return true;
return x.Bar == y.Bar && x.Name == y.Name && return x.Day == y.Day;
}
public int GetHashCode(Foo obj)
{
unchecked
{
var hashCode = obj.Bar;
hashCode = (hashCode * 397) ^ (obj.Name != null ? obj.Name.GetHashCode() : 0);
hashCode = (hashCode * 397) ^ (int) obj.Day; 0);
return hashCode;
}
}
}
// Compares only in Foo.Bar
public class FooBarComparer : IEqualityComparer<Foo>
{
public bool Equals(Foo x, Foo y)
{
if (ReferenceEquals(x, y)) return true;
return x.Bar == y.Bar;
}
public int GetHashCode(Foo obj)
{
unchecked
{
var hashCode = obj.Bar;
hashCode = (hashCode * 397) ^ (obj.Name != null ? obj.Name.GetHashCode() : 0);
hashCode = (hashCode * 397) ^ (int) obj.Day; 0);
return hashCode;
}
}
}
// Compares only in Foo.Name
public class FooNameComparer : IEqualityComparer<Foo>
{
public bool Equals(Foo x, Foo y)
{
if (ReferenceEquals(x, y)) return true;
return x.Name == y.Name;
}
public int GetHashCode(Foo obj)
{
unchecked
{
var hashCode = obj.Bar;
hashCode = (hashCode * 397) ^ (obj.Name != null ? obj.Name.GetHashCode() : 0);
hashCode = (hashCode * 397) ^ (int) obj.Day; 0);
return hashCode;
}
}
}
// Compares only in Foo.Day
public class FooDayComparer : IEqualityComparer<Foo>
{
public bool Equals(Foo x, Foo y)
{
if (ReferenceEquals(x, y)) return true;
return x.Day == y.Day;
}
public int GetHashCode(Foo obj)
{
unchecked
{
var hashCode = obj.Bar;
hashCode = (hashCode * 397) ^ (obj.Name != null ? obj.Name.GetHashCode() : 0);
hashCode = (hashCode * 397) ^ (int) obj.Day; 0);
return hashCode;
}
}
}
Question
I want to allow the user to be able to combine multiple Comparer
types to evaluate two instances of Type Foo
. I'm not sure how to do that.
Idea
What I came up with is something like this, where I AND
the results of comparisons done by all comparers in the list:
bool CompareFoo(Foo a, Foo b, params IComparer[] comparers)
{
bool isEqual = true;
// Or the list and return;
foreach (var comparer in comparers)
{
isEqual = isEqual && comparer.Equals(x,y);
}
return isEqual;
}
Notes
- My target .NET version is
4.5
. - I may be stuck with
C# 5.0
. - Also, may be stuck with `MSBuild 12.0
- This is my first time to use
IComparer
.