c# Linq distinct不会调用Equals方法详解
我有以下课程
publicclassModInfo:IEquatable{ publicintID{get;set;} publicstringMD5{get;set;} publicboolEquals(ModInfoother) { returnother.MD5.Equals(MD5); } publicoverrideintGetHashCode() { returnMD5.GetHashCode(); } }
我使用如下方法将一些数据加载到该类的列表中:
publicvoidReloadEverything(){ varbeforeSort=newList(); //Bunchofloadingfromlocalsqlitedatabase. //notincludedsinceit'sreloadboringtolookat varmodinfo=beforeSort.OrderBy(m=>m.ID).AsEnumerable().Distinct().ToList(); }
问题是Distinct()调用似乎没有做到这一点.仍然存在彼此相等的对象.
根据这篇文章:https://msdn.microsoft.com/en-us/library/vstudio/bb348436%28v=vs.100%29.aspx
这就是你应该如何做出不同的工作,但它似乎并没有在ModInfo对象上调用Equals方法.
是什么导致这种情况发生?
示例值:
modinfo[0]:id=2069,MD5=0AAEBF5D2937BDF78CB65807C0DC047C
modinfo[1]:id=2208,MD5=0AAEBF5D2937BDF78CB65807C0DC047C
我不关心选择哪个值,因为md5值相同,它们可能是相同的.
您还需要覆盖Object.Equals,而不仅仅是实现IEquatable.
如果你把它添加到你的班级:
publicoverrideboolEquals(objectother) { ModInfomod=otherasModInfo; if(mod!=null) returnEquals(mod); returnfalse; }
它应该工作.
有关详细信息,请参阅此文章:ImplementingIEquatableProperly
编辑:好的,这是基于GetHashCode的最佳实践的略有不同的实现.
publicclassModInfo:IEquatable{ publicintID{get;set;} publicstringMD5{get;set;} publicboolEquals(ModInfoother) { if(other==null)returnfalse; return(this.MD5.Equals(other.MD5)); } publicoverrideintGetHashCode() { unchecked { inthash=13; hash=(hash*7)+MD5.GetHashCode(); returnhash; } } publicoverrideboolEquals(objectobj) { ModInfoother=objasModInfo; if(other!=null) { returnEquals(other); } else { returnfalse; } } }
你可以验证它:
ModInfomod1=newModInfo{ID=1,MD5="0AAEBF5D2937BDF78CB65807C0DC047C"}; ModInfomod2=newModInfo{ID=2,MD5="0AAEBF5D2937BDF78CB65807C0DC047C"}; //Youshouldgettruehere boolareEqual=mod1.Equals(mod2); Listmods=newList {mod1,mod2}; //Youshouldget1resulthere mods=mods.Distinct().ToList();
What'swiththosespecificnumbersinGetHashCode?
补充知识:C#中通过Distinct方法对List集合进行去重
在C#的List集合对象中,可以使用Distinct方法来对List集合元素进行去重,如果list集合内部元素为值类型,则Distinct方法根据值类型是否相等来判断去重,如果List集合内部元素为引用类型变量,则是判断相同引用的对象为相同进行List集合元素去重操作。
(1)值类型的List集合对象intList,内部元素为1,1,2,2,3,4,5等这几个元素。对intList对象进行去重可使用下列语句:
ListintList=newList(){1,1,2,2,3,4,5};
intList=intList.Distinct().ToList();
经过上述Distinct方法去重处理并重新赋值后,intList集合内部元素为:1,2,3,4,5。
(2)针对引用类型的Distinct方法去重,则是判断List集合中的对象引用地址是否一致,不一致的话为不同的两个对象,即使2个对象的每个属性值都一样的情况下。
ListtestList=newList(); testList.Add(newTestModel() { Index=1, Name=“Index1” }); testList.Add(newTestModel() { Index=2, Name=“Index2” }); testList.Add(newTestModel() { Index=2, Name=“Index2” }); testList=testList.Distinct().ToList();
上述程序语句中,虽然List集合testList中的第2个元素和第3个元素的属性值完全一样,但这2个元素依旧是不同的对象,因此在调用Distinct()方法去重后重新赋值,testList依旧不变。
以上这篇c#Linqdistinct不会调用Equals方法详解就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持毛票票。
声明:本文内容来源于网络,版权归原作者所有,内容由互联网用户自发贡献自行上传,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任。如果您发现有涉嫌版权的内容,欢迎发送邮件至:czq8825#qq.com(发邮件时,请将#更换为@)进行举报,并提供相关证据,一经查实,本站将立刻删除涉嫌侵权内容。