I have an Entity that doesn't override any of the equality members\operators.
When comparing two proxies of them (I got them from the Nhibernate session
) the result changes according to the equality method:
- ReferenceEquals(first, second) - false.
- first == second - false
- Equals(first, second) - true.
This is even more weird as they both exist in the same session context and according to the Nhibernate docs:
NHibernate only guarantees identity ( a == b , the default implementation of Equals()) inside a single ISession!`
And:
The instance is currently associated with a persistence context. It has a persistent identity (primary key value) and, perhaps, a corresponding row in the database. For a particular persistence context, NHibernate guarantees that persistent identity is equivalent to CLR identity (in-memory location of the object).
So why not all of the equality methods return true?
Update:
I get the enteties this way, Query the session for ChildEntity and get the Parents Entities with Linq's select
, similar to this:
var childs = session.Query<Child>();
var parents = childs.Select(x => x.ParentEntity).ToList();
If
ReferenceEquals
returns false, you are clearly comparing two different instances.Equals might still be true if it's overridden, but I don't think that's where the actual problem is.
I'd like to know how you're mapping and getting those objects, because as the docs say, you can never get two different objects of the same type representing the same row in the same session.
After I get
childs
from the session I Merge them with the session.It appear that the merge detached the entity from the session and return a new Proxy attached to the session.
It can be fixed with
Edit
You might be using a struct? See below
I suppose reference types show the behaviour you expect:
Prints:
For structs, things are different (commeting out the
a==b
test, which doesn't compile for structs:)Output:
Rationale:
The default implementation of Equals() comes from class
ValueType
, which is implicit base class of all value types. You may override this implementation by defining your own Equals() method in your struct.ValueType.Equals()
always returns false when one compares objects of different (dynamic) types. If objects are of the same type, it compares them by callingEquals()
for each field. If any of these returns false, the whole process is stopped, and final result is false. If all field-by-field comparisons return true, final result is true