Skip to content

Instantly share code, notes, and snippets.

@milleniumbug
Created November 21, 2017 09:01
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save milleniumbug/c376727a259bb0b4fe7d7a25bb051ca9 to your computer and use it in GitHub Desktop.
Save milleniumbug/c376727a259bb0b4fe7d7a25bb051ca9 to your computer and use it in GitHub Desktop.
public class ValueBased<T> : IEquatable<ValueBased<T>>
{
private static readonly IReadOnlyList<FieldInfo> fields;
static ValueBased()
{
fields = typeof(T).GetRuntimeFields().Where(field => !field.IsStatic).ToList();
}
/// <inheritdoc />
public bool Equals(ValueBased<T> other)
{
foreach(var field in fields)
{
var left = field.GetValue(this);
var right = field.GetValue(other);
if(object.ReferenceEquals(left, right))
continue;
if(left == null && right != null)
return false;
if(!left.Equals(right))
return false;
}
return true;
}
/// <inheritdoc />
public override bool Equals(object obj)
{
if(ReferenceEquals(null, obj)) return false;
if(ReferenceEquals(this, obj)) return true;
if(obj.GetType() != this.GetType()) return false;
return Equals((ValueBased<T>) obj);
}
/// <inheritdoc />
public override int GetHashCode()
{
return fields.Aggregate(17, (current, field) => 37 * current + field.GetValue(this).GetHashCode());
}
public static bool operator ==(ValueBased<T> left, ValueBased<T> right)
{
return Equals(left, right);
}
public static bool operator !=(ValueBased<T> left, ValueBased<T> right)
{
return !Equals(left, right);
}
public T Clone()
{
return (T) this.MemberwiseClone();
}
/// <inheritdoc />
public override string ToString()
{
var sb = new StringBuilder();
sb.Append(typeof(T).FullName);
sb.Append("{ ");
bool first = true;
foreach(var field in fields)
{
if(!first)
{
sb.Append(", ");
}
sb.Append(field.Name);
sb.Append(" = ");
sb.Append(field.GetValue(this));
first = false;
}
sb.Append(" }");
return sb.ToString();
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment