C#比較對象的相等性

? ?對于相等的機制全部不同,這取決于比較的是引用類型還是值類型。以下分別介紹引用類型和值類型的相等性。

1.比較引用類型的相等性

? ?System.Object定義了三種不同的方法,來比較對象的相等性:ReferenceEquals()和兩個版本號的Equals()。再加上比較運算符(==)。實際上有4種進行比較相等的方式。

1.1 ReferenceEquals()方法

命名控件: System

程序集:mscorlib.dll

語法:public static bool ReferenceEquals(Object objA, Object objB)

能夠看出ReferenceEquals()是一個靜態方法,確定指定的Object實例是否是同樣的實例。作為靜態方法。所以不能重寫。

1.1.1 使用ReferenceEquals()方法比較值類型

int int1 = 3;

bool B1 = Object.ReferenceEquals(int1, int1);//B1為false

? ? 因為objA和objB是值類型,首先進行裝箱。然后傳遞給ReferenceEquals()方法。這意味著,即使objA和objB表示值類型的同一個實例,ReferenceEquals()方法也返回false。

1.1.2 使用ReferenceEquals()方法比較字符串

String s1 = "String1";

String s2 = "String1";

bool B2 = Object.ReferenceEquals(s1, s2);//true

String suffix = "A";

String s3 = "String" + suffix;

String s4 = "String" + suffix;

bool B3 = Object.ReferenceEquals(s3, s4);//false

? ? 當比較字符串時 假設 objA 和 objB 是字符串,假設該字符串會暫留,ReferenceEquals 方法返回 true。 它不運行值相等測試。

在以下的演示樣例中。由于它們是一個暫存的字符串的兩個實例,s1 和 s2 相等。 可是,s3 和 s4 不相等,由于雖然它們是具有同樣的字符串值。字符串不會暫留。

1.1.3 使用ReferenceEquals()比較兩個對象

object o = null;

object p = null;

object q = new Object();

bool B4 = Object.ReferenceEquals(o, p);//true

p = q;

bool B5 = Object.ReferenceEquals(p, q);//true

bool B6 = Object.ReferenceEquals(o, p);//false

1.2 Equals()方法

1.2.1 虛擬的Equals()方法

命名空間: System

程序集:mscorlib(在mscorlib.dll中)

語法:public virtual bool Equals(Object obj)

? ? Equals()虛擬版本號的System.Object實現代碼也比較引用。

但由于這種方法是虛擬的。所以能夠在自己的類中重寫它。按值來比較對象。

特別是假設希望類的實例用作字典中的鍵,就須要重寫這種方法,以比較值。否則。依據重寫Object.GetHashCode()的方式。包括對象的字典類要么不工作,要么工作的效率很低。在重寫Equals()方法時要注意,重寫的代碼不會拋出異常。這是由于假設拋出異常。字典類就會出問題,一些在內部調用這種方法的.NET基類也可能出問題。

? ? Equals 是一個虛方法。同意不論什么類重寫事實上現。

表示某個值(本質上能夠是不論什么值類型)或一組值(如復數類)的不論什么類都應該重寫 Equals。假設類型要實現 IComparable,則它應該重寫 Equals。

Equals 的新實現應該遵循 Equals 的全部保證:

x.Equals(x) 返回 true。

x.Equals(y) 與 y.Equals(x) 返回同樣的值。

假設 (x.Equals(y) && y.Equals(z)) 返回 true,則 x.Equals(z) 返回 true。

僅僅要不改動 x 和 y 所引用的對象,x.Equals(y) 的興許調用就返回同樣的值。

x.Equals(null) 返回 false。

? ? Equals 的新實現不應該引發異常。建議重寫 Equals 的不論什么類同一時候也重寫 System.Object.GetHashCode。

除了實現 Equals(對象)外。還建議全部的類為自己的類型實現 Equals(類型)以增強性能。

比如:

class TwoDPoint : System.Object

{

public readonly int x, y;

public TwoDPoint(int x, int y) //constructor

{

this.x = x;

this.y = y;

}

public override bool Equals(System.Object obj)

{

// If parameter is null return false.

if (obj == null)

{

return false;

}

// If parameter cannot be cast to Point return false.

TwoDPoint p = obj as TwoDPoint;

if ((System.Object)p == null)

{

return false;

}

// Return true if the fields match:

return (x == p.x) && (y == p.y);

}

public bool Equals(TwoDPoint p)

{

// If parameter is null return false:

if ((object)p == null)

{

return false;

}

// Return true if the fields match:

return (x == p.x) && (y == p.y);

}

public override int GetHashCode()

{

return x ^ y;

}

}

1.2.2 靜態的Equals()方法

命名空間: System

程序集:mscorlib(在mscorlib.dll中)

語法:public static bool Equals(Object objA, Object objB)

Dog m1 = new Dog("Alaskan Malamute");

Dog m2 = new Dog("Alaskan Malamute");

Dog g1 = new Dog("Great Pyrenees");

Dog g2 = g1;

Dog d1 = new Dog("Dalmation");

Dog n1 = null;

Dog n2 = null;

Console.WriteLine("null = null: {0}", Object.Equals(n1, n2));//true

Console.WriteLine("null Reference Equals null: {0}\n", Object.ReferenceEquals(n1, n2));//true

Console.WriteLine("{0} = {1}: {2}", g1, g2, Object.Equals(g1, g2));//true

Console.WriteLine("{0} Reference Equals {1}: {2}\n", g1, g2, Object.ReferenceEquals(g1, g2));//true

Console.WriteLine("{0} = {1}: {2}", m1, m2, Object.Equals(m1, m2));//true

Console.WriteLine("{0} Reference Equals {1}: {2}\n", m1, m2, Object.ReferenceEquals(m1, m2));//false

Console.WriteLine("{0} = {1}: {2}", m1, d1, Object.Equals(m1, d1)); //false Console.WriteLine("{0} Reference Equals {1}: {2}", m1, d1, Object.ReferenceEquals(m1, d1)); //false?

? ? 靜態 Equals(Object, Object) 方法指示兩個對象。objA 和 objB,是否相等

? ? 它確定兩個對象是否表示同一對象引用。 假設成功,該方法返回 true. 這測試與調用 ReferenceEquals 方法等效。 另外。假設 objA 和 objB 都為 null,則方法返回 true。

它確定 objA 或 objB 是否 null。 假設是這樣。則返回 false。

? ? 假設兩個對象不表示同一對象引用,且均不為 null,它調用 objA。

Equals(objB) 而且返回結果。

這意味著。假設 objA 重寫 Object.Equals(Object) 方法,該重寫調用。

1.3 比較運算符(==)

? ? 對于引用類型,== 默認的行為與ReferenceEquals的行為同樣,僅有兩個對象指向同一個Reference的時候才返回true。可是.NET Framework中的類非常多對==進行了重載,比如String類的==與Equals的行為同樣。推斷兩個字符串的內容是否相等。所以在應用中。對于 系統定義的引用類型建議不要使用==操作符,以免程序出現與預期不同的執行結果。

重載的運算符 == 實現不應引發異常。重載運算符 == 的不論什么類型還應重載運算符 !=。

比如:

public static bool operator ==(ThreeDPoint a, ThreeDPoint b)

{

// If both are null, or both are same instance, return true.

if (System.Object.ReferenceEquals(a, b))

{

return true;

}

// If one is null, but not both, return false.

if (((object)a == null) || ((object)b == null))

{

return false;

}

// Return true if the fields match:

return a.x == b.x && a.y == b.y && a.z == b.z;

}

public static bool operator !=(ThreeDPoint a, ThreeDPoint b)

{

return !(a == b);

}

2.比較值類型的相等性

? ? 在比較值類型的相等時,採用與引用類型同樣的規則:ReferenceEquals()用于比較引用,Equals()用于比較值,比較運算發能夠看做是一個中間項。但最大的差別是值類型須要裝箱。才干把他們轉換為引用。

ReferenceEquals()在應用于值類型時。總是返回false。

由于調用這種方法,須要裝箱。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/282235.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/282235.shtml
英文地址,請注明出處:http://en.pswp.cn/news/282235.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

WebSocket教程

一、為什么需要 WebSocket? 初次接觸 WebSocket 的人,都會問同樣的問題:我們已經有了 HTTP 協議,為什么還需要另一個協議?它能帶來什么好處? 答案很簡單,因為 HTTP 協議有一個缺陷&#xff1a…

C# WPF十個美觀的界面設計展示

概述很多時候,我們設計的界面總是感覺缺乏美感,不是我們不會開發好看的界面,而是不知道怎么才算美觀,這時候我們不妨看看別人好的頁面是怎么做的.下面展示一些我覺得做的比較好的cs界面,希望能給大家在平時做界面設計時…

BZOJ3172: [Tjoi2013]單詞

【傳送門:BZOJ3172】 簡要題意: 給出n個單詞,你可以理解為將這些單詞變成一個個段落,然后求出每個單詞在所有段落中出現的次數 題解(一): 剛開始不是很懂題目,結果發現將所有單詞看成…

MySQL5.6二進制軟件包編譯安裝詳解(三)

一、軟件環境 [rootlocalhost ~]# uname -r 3.10.0-862.el7.x86_64 [rootlocalhost ~]# cat /etc/redhat-release CentOS Linux release 7.5.1804 (Core) 二、安裝部署過程詳解 MySQL安裝3種方式:1>rpm包安裝應用文件默認安裝在/usr/local 目錄下2>源碼編譯需…

Java反射學習總結五(Annotation(注解)-基礎篇)

Annotation(注解)簡單介紹: 注解大家印象最深刻的可能就是JUnit做單元測試,和各種框架里的使用了。本文主要簡介一下注解的用法,下篇文章再深入的研究。 annotation并不直接影響代碼語義。可是它可以被看作類似程序的工具或者類庫。它會反過來對正在執行…

使用autok3s 安裝k3s 集群 和 kuboard 管理集群

一、k3s介紹1.1 什么是k3s?k3s 是經過 CNCF 認證的由 Rancher 公司開發維護的一個輕量級的 Kubernetes 發行版,內核機制還是和 k8s 一樣,但是剔除了很多外部依賴以及 K8s 的 alpha、beta 特性,同時改變了部署方式和運行方式,目的…

Nginx—— Rewrite規則的使用

一、使用場景 1、URL訪問跳轉 (1)頁面跳轉 (2)兼容性支持(比如新老版本交替時,給老版本一條訪問道路) (3)展示效果(比如縮短前臺界面的地址欄的url&#…

java對象實例化的方式

java對象實例化的方式有以下幾種:1、使用new2、工廠模式3、反射4、clone()方法5、反序列化方式 /** 實現Cloneable和Serializable接口 */public class Book implements Cloneable, Serializable {private static final long serialVersionUID 1L; private Integer …

iOS-生成二維碼圖片【附中間帶有小圖標二維碼】(QRCode)

生成二維碼圖片也是項目中常用到的,二維碼的掃描Git上有很多好用的,這里主要說下二維碼的生成 1.普通二維碼 方法 /**生成二維碼QRStering:字符串imageFloat:二維碼圖片大小*/ (UIImage *)createQRCodeWithString:(NSString *)QRS…

libubox

lbubox是openwrt的一個核心庫,封裝了一系列基礎實用功能,主要提供事件循環,二進制格式處理,linux鏈表實現和一些JSON輔助處理。 它的目的是以動態鏈接庫方式來提供可重用的通用功能,給其他模塊提供便利和避免再造輪子。…

社區糾紛不斷:程序員何苦為難程序員

出品 | OSC開源社區(ID:oschina2013)今年年初,我們報道“因為被多人侮辱大吼,Swift 之父正式退出 Swift 核心團隊”。諸如此類的“語言暴力”、“網絡暴力”事件在開源社區乃至整個 IT 社區屢見不鮮。多個技術社區,都出…

PHP 分布式集群中session共享問題以及session有效期的設置

一、Session的原理 以下以默認情況舉例: session_start();之后,會生成一個唯一的session_id,每一個用戶對應唯一一個session_id,每一個session_id對應服務器端的一個session文件。這個session文件存儲著當前session_id的信息&am…

[SDOI2009]Bill的挑戰——全網唯一 一篇容斥題解

全網唯一一篇容斥題解 Description Solution 看到這個題,大部分人想的是狀壓dp 但是我是個蒟蒻沒想到,就用容斥切掉了。 并且復雜度比一般狀壓低, (其實這個容斥的算法,提出來源于ywy_c_asm) (然…

[NOIP2015提高組]運輸計劃

題目:BZOJ4326、洛谷P2680、Vijos P1983、UOJ#150、codevs4632、codevs5440。 題目大意:有一棵帶權樹,有一些運輸計劃,第i個運輸計劃從ai到bi,耗時為ai到bi的距離,所有運輸計劃一起開始。現在可以把一條邊權…

對象存儲OSS服務

一、oss是什么 阿里云對象存儲服務(Object Storage Service,簡稱OSS)為您提供基于網絡的數據存取服務。使用OSS,您可以通過網絡隨時存儲和調用包括文本、圖片、音頻和視頻等在內的各種非結構化數據文件。 阿里云OSS將數據文件以…

《Access 2007開發指南(修訂版)》一一1.5 什么是數據庫對象

本節書摘來自異步社區出版社《Access 2007開發指南(修訂版)》一書中的第1章,第1.5節,作者: 【美】Alison Balter,更多章節內容可以訪問云棲社區“異步社區”公眾號查看。 1.5 什么是數據庫對象 Access 2007開發指南(修訂版)正如前…

ETL工具kettle的組件--生成記錄

今天介紹下kettle的一個比較實用的組件——生成記錄;當我們想將一部分文本數據變成數據行,每個字段作為一個數據行的一個列,那么我們可以利用這個組件;它的位置在雙擊點開根據自己的實際需要進行設置當設置后,可以點擊…

Linux學習筆記一

linux  kernel lib module shell tools ls -la: 顯示所有文件包括隱藏文件  cat /proc/cpuinfo: 顯示cpu信息 man man  /string: 向上搜索string字符串 繼續按下小寫n向上搜索  ?string: 向下搜索string字符串 繼續按下大…

PHP中路由和rewrite的使用

一、場景介紹: 1、簡化url地址,方便大家記憶 2、有利于搜索引擎優化 3、安全(讓用戶看不出網站的目錄結構) 舉例:比如我這里將main控制器中的bb方法路由到kk,這樣,我們a標簽請求跳轉到cp.xi…

《NoSQL權威指南》導讀

引言 NoSQL權威指南“沒有什么會比引入新秩序更難,因為創新者必須要面對那些在舊環境中已經做得很好的對手,以及那些在新環境中做得很好的冷漠者。” ——Niccolo Machiavelli [1] 在過去的幾十年,我已經通過Elsevier/Morgan Kaufmann出版社出…