網站首頁 編程語言 正文
應用情景:
很多標準的方法都是利用Object.Equals方法來做對比的,例如LIst.Remove
假設 某些情景下我們希望引用類型判斷“相等”時不去看地址是不是同一個,而是看某些屬性是不是一樣就可以了。(例如身份證ID是一個就認為是同一個人)
復寫方法如下范例所示:
Main{
List<People> nList = new List<People> { new People( 1 ), new People( 2 ), new People( 3 ) };
People onePeople = new People( 1 );
nList.Remove( onePeople );
}
class People
{
public People( int nID )
{
ID = nID;
}
int ID;
public override bool Equals( object obj )
{
return Equals( obj as People );
}
bool Equals( People other )
{
return other != null
&& ID == other.ID;
}
}
P.s. 最好也重新overide GetHashCode方法:
(7跟13只是常用的手法,拿質數來乘,確保hash code是獨一無二),也可以加入 ^ 計算
public override int GetHashCode()
{
int hash =13;
hash = (hash * 7) + ID== null ? 0 : ID.GetHashCode();
}
原因是:
1.Equal是判斷是否指向同一個地址
2.每個對象都會有一個獨一無二的HashCode
一旦override了Equal方法,卻不override GetHashCode方法會導致兩個判斷為相同(利用Equal判斷)的對象,Hash值卻不同。
承上,在使用到HashCode的地方(例如Dictionary中的key),兩個相同對象可能會被重復加入到Dictionary中
什么時候需要重寫 Equals() 方法
引用類型:
只有當需要修改該引用類型所定義的語義時,才應該重寫實例版本的 Equals() 方法。如果類型需要采用值語義而不是引用語義(或者說,需要按照對象內容而不是對象身份來進行比較),那么就應該針對這個類型重寫實例版本的 Object.Equals() 方法。
引用類型一般不需要重寫 operator==()。
值類型:
創建值類型的時候,總是應該針對這個類型重寫 ValueType.Equals() 方法。
因為值類型都繼承自 System.ValueType 類,System.ValueType 類默認通過反射來實現比較,效率不夠高。
值類型中默認的 == 運算符會默認通過反射進行比較,因此,也應該重寫 == 操作符。
重寫 Equals() 方法時的注意事項
Equals() 方法必須滿足等同關系的 3 項數學性質:自反性、對稱性、可傳遞性。
Equals() 方法決不應該拋出異常。
重寫 Equals() 方法時,只有在基類型的 Equals(object) 不是由 System.Object 或 System.ValueType 所提供的情況下,才需要調用基類型的版本。
重寫 Equals() 的時候,還應該讓該類型實現 IEquatable<T> 接口。
重寫 Equals() 方法后,通常應該同時重寫 GetHashCode() 方法。
重寫 GetHashCode() 方法時的注意事項
如果 Equals() 方法認定兩個對象相等,那么這兩個對象的 HashCode 也必須相同;
對任意對象來說,其 HashCode 必須在生命周期內保持不變;
HashCode 計算方法應該將其值均勻地映射到各個整數上,避免堆集。
一種常用的 HashCode 算法是:對類型中的每個相互獨立的不可變字段調用 GetHashCode() 方法,并對返回的 HashCode 進行異或(XOR)運算,將得到的最終結果作為對象本身的 HashCode 。
原文鏈接:https://blog.csdn.net/qq_41617697/article/details/123716144
相關推薦
- 2023-01-10 Docker調度器Kubernetes使用過程_docker
- 2022-07-02 TiDB中的RocksDB讀寫和Raft日志同步
- 2023-08-13 基于TP5框架的excel導入功能
- 2022-03-25 如何使用postman(postman的使用方法詳解)
- 2022-04-25 在?Python?中進行?One-Hot?編碼_python
- 2022-11-05 Nginx配置文件nginx.conf的基本配置實例詳解_nginx
- 2022-07-15 Android自定義view繪制表格的方法_Android
- 2022-10-16 Python實現自定義Jupyter魔法命令_python
- 最近更新
-
- window11 系統安裝 yarn
- 超詳細win安裝深度學習環境2025年最新版(
- Linux 中運行的top命令 怎么退出?
- MySQL 中decimal 的用法? 存儲小
- get 、set 、toString 方法的使
- @Resource和 @Autowired注解
- Java基礎操作-- 運算符,流程控制 Flo
- 1. Int 和Integer 的區別,Jav
- spring @retryable不生效的一種
- Spring Security之認證信息的處理
- Spring Security之認證過濾器
- Spring Security概述快速入門
- Spring Security之配置體系
- 【SpringBoot】SpringCache
- Spring Security之基于方法配置權
- redisson分布式鎖中waittime的設
- maven:解決release錯誤:Artif
- restTemplate使用總結
- Spring Security之安全異常處理
- MybatisPlus優雅實現加密?
- Spring ioc容器與Bean的生命周期。
- 【探索SpringCloud】服務發現-Nac
- Spring Security之基于HttpR
- Redis 底層數據結構-簡單動態字符串(SD
- arthas操作spring被代理目標對象命令
- Spring中的單例模式應用詳解
- 聊聊消息隊列,發送消息的4種方式
- bootspring第三方資源配置管理
- GIT同步修改后的遠程分支