我有一个私有类,User实现了一个接口,IQMUser,带有
public static bool operator ==( User a, User b ) { return Equals( a, b ); }
public static bool operator !=( User a, User b ) { return !Equals( a, b ); }
public override bool Equals ( object obj )
{
User other = obj as User;
return m_LMUser.UserID == other.m_LMUser.UserID;
}
public override int GetHashCode ( )
{
return m_LMUser.GetHashCode ( );
}
User是公共类UserManager的成员,它具有GetUsers(),返回IList<IQMUser>
。在另一堂课中,我有
IQMUser otherUser = UserManager.GetUsers( )
.Where( u => u != CurrentUser )
.FirstOrDefault( );
现在,我知道GetUsers返回的对象与CurrentUser具有相同的m_LMUser.UserID。但是,即使在这种情况下,测试u!= CurrentUser始终为真。
我在每个操作符重载和User中的Equals覆盖中设置了断点,但没有一个命中。
然后我将查询更改为
IQMUser otherUser = UserManager.GetUsers( )
.Where( u => !u.Equals( CurrentUser ) )
.FirstOrDefault( );
按预期方式点击重写的Equals方法。
我的运算符重载有什么问题,Linq甚至没有击中它们?
答案 0 :(得分:1)
从它的外观来看,你的==实现是调用静态Object.Equals方法而不是你的实例equals方法。这将检查两个引用是否指向同一块内存(http://msdn.microsoft.com/en-us/library/w4hkze5k.aspx)
将其更改为:
public static bool operator ==( User a, User b ) { return a.Equals(b); }
public static bool operator !=( User a, User b ) { return !a.Equals(b); }
你还应该将你的equals方法更改为:
public override bool Equals ( object obj )
{
User other = obj as User;
return !Object.ReferenceEquals(other, null) && m_LMUser.UserID == other.m_LMUser.UserID;
}
答案 1 :(得分:1)
如果我正确理解了你的继承层次结构,那么“Where”中的类型似乎是IQMUser
(基类),而operator ==
是在子类User
上实现的。
由于operator ==
非虚拟 ,因此类型为IQMUser
的Linq Where表达式将运行IQMUser operator ==
而不是User
在{{1}}上实施。
另一方面,等于是虚拟,并且覆盖按原样运行,如果直接调用它,它可以正常工作。