generating equals/gethashcode ignores automatic properties

well as the subject says, when generating the equals and gethashcode implementations, automatic properties are ignored... is this by design? or should i report a bug for this?

7 comments
Comment actions Permalink

Davy,

OT: I'm curious. I see quite a few references here and there to the hash code in .Net. I've never had a need to use it directly but maybe I'm not working on the right applications that need to. Could you give me a real-world example, perhaps from your experience, as to why you need to use hash codes in your code? I'm obviously missing the bigger picture but I'd appreciate a brief explanation if you could firnd the time to do so.

0
Comment actions Permalink

i often make use of the Value Object pattern... for that you basically need to override the Equals method to properly compare two instances of the same class based on their respective inner-values.

and if you override Equals, you should override the GetHashCode method as well... for a good explanation on why this is necessary, take a look at this:
http://musingmarc.blogspot.com/2007/08/vtos-rtos-and-gethashcode-oh-my.html

0
Comment actions Permalink

Can I jump in here and ask a question?

I have the following code

public interface IPrimaryKey
{
int Value {get; set;}
bool IsNewRecord {get;}
}

and a struct that implements it:

public struct PrimaryKey : IPrimaryKey
{
public int Value {get; set;}
public bool IsNewRecord {get;}

public PrimaryKey(int key) : this() { Value =
key; }

public override bool Equals(object obj)
{
if (obj == null) {return false; }

var key = (IPrimaryKey) obj;

return Value == key.Value;
}

public static bool operator ==(PrimaryKey a, PrimaryKey b)
{
if ((object)a == null || (object)b == null) { return false; }

return (a.Value == b.Value);
}

public static bool operator !=(PrimaryKey a, PrimaryKey b)
{ return !(a == b); }
}

This works fine for the following:

PrimaryKey keyA = new PrimaryKey(99);
PrimaryKey keyB = new PrimaryKey(99);

Assert.IsTrue(keyA == keyB); // ok
Assert.IsFalse(keyA != keyB); //ok
Assert.IsTrue(keyA.Equals(keyB); //ok

However equality (== and !=) does not work for this:
IPrimaryKey keyA = new PrimaryKey(99);
IPrimaryKey keyB = new PrimaryKey(99);

Assert.IsTrue(keyA == keyB); // fails
Assert.IsFalse(keyA != keyB); //fails
Assert.IsTrue(keyA.Equals(keyB); //ok

I'm just starting to get my head around writing to implementations and so am
trying to use interfaces everywhere!! I'm probably barking up the wrong tree
here ...
Is there a way to override the operator on an interface?

Thanks
Jeremy




"Davy Brion" <no_replay@jetbrains.com> wrote in message
news:2319673.1205495586298.JavaMail.itn@is.intellij.net...
>i often make use of the Value Object pattern... for that you basically need
>to override the Equals method to properly compare two instances of the same
>class based on their respective inner-values.
>

and if you override Equals, you should override the GetHashCode method as
well... for a good explanation on why this is necessary, take a look at
this:
http://musingmarc.blogspot.com/2007/08/vtos-rtos-and-gethashcode-oh-my.html


0
Comment actions Permalink

i don't think so... adding an operator to an interface simply gives an "interfaces cannot contain operators" compiler error

you can get it working if you replace the interface with an abstract class and then define the operators on that. but then PrimaryKey would have to be a class instead of a struct though...

0
Comment actions Permalink

You're quite right - I changed the struct to class and it's working fine
now.
Thanks
Jeremy


"Davy Brion" <no_replay@jetbrains.com> wrote in message
news:9257560.1205574235659.JavaMail.itn@is.intellij.net...
>i don't think so... adding an operator to an interface simply gives an
>"interfaces cannot contain operators" compiler error
>

you can get it working if you replace the interface with an abstract class
and then define the operators on that. but then PrimaryKey would have to
be a class instead of a struct though...


0
Comment actions Permalink

Another good reason not to have structs implementing interfaces is that you incur a boxing operation should you obtain a reference to your struct using the interface. you lose the benefits of storing the struct in stack memory, and box/unbox operations are slow. for more info see:

C# Heap(ing) Vs Stack(ing) in .NET: Part I

- Oisin

Edited by: Oisin Grehan on Mar 20, 2008 1:53 AM

0
Comment actions Permalink

apparantly this has been fixed (at least it works now in build 755)

0

Please sign in to leave a comment.