摘要:小概與,這三個(gè)操作在程序當(dāng)中滿地都是,特別是容器里,如中的哈希映射與搜索元素就是根據(jù)和判斷的,所以如何正確的理解和使用顯得非常重要,并且在封裝類的時(shí)候,十分建議通通重寫我們先要知道這個(gè)概念,每個(gè)線程都有屬于自己的虛擬機(jī)棧,虛擬機(jī)棧中的元素我
小概
==,hashCode() 與 equals() ,這三個(gè)操作在 Java 程序當(dāng)中滿地都是,特別是容器里,如 Map 中的哈希映射與搜索元素就是根據(jù)
hashCode() 和 equals() 判斷的,所以如何正確的理解和使用顯得非常重要,并且在封裝類的時(shí)候,十分建議通通重寫
我們先要知道這個(gè)概念,每個(gè)線程都有屬于自己的 虛擬機(jī)棧,虛擬機(jī)棧中的元素我們稱之為 棧幀,每運(yùn)行一個(gè)方法時(shí),虛擬機(jī)會(huì)為這個(gè)方法創(chuàng)建一個(gè)棧幀,并入棧,方法結(jié)束后便出棧
那么我們操作的變量有兩種
局部變量:存在當(dāng)前棧幀的局部變量表里,如果是基本數(shù)據(jù)類型便是值的大小,如果是對(duì)象便是一個(gè)指向堆內(nèi)存中對(duì)象地址的引用
全部變量:存在方法區(qū)中,存儲(chǔ)規(guī)則一樣
所以我們比較的,是 基本數(shù)據(jù)類型的大小 和 引用地址
a == b比較規(guī)則
當(dāng)a,b 為對(duì)象時(shí),表示兩者 引用地址 是否相同,即堆內(nèi)存中地址是否相同
當(dāng)a,b 為基本數(shù)據(jù)類型時(shí),表示兩者 數(shù)據(jù)大小 是否相等
a.equals(b)假設(shè) a 的對(duì)象類型為 A
比較規(guī)則a,b 只能為對(duì)象,表示兩者 對(duì)象屬性 是否相等,如 String 就是比較內(nèi)部維護(hù)的 char[] 數(shù)組每一個(gè)字符是否相等
為了簡化比較復(fù)雜度,往往會(huì)先判斷 a == b,如果它們都指向同一個(gè)地址,那么兩者內(nèi)容肯定一樣,則不需要逐一比較對(duì)象內(nèi)容中的值
我們可以認(rèn)為,== 和 equals 的推導(dǎo)關(guān)系是 充分不必要 的
== 成立則 equals 成立
equals 成立,== 不一定成立
如何比較屬性比如區(qū)分兩個(gè)學(xué)生是否是同一個(gè)學(xué)生,我們其實(shí)只需要查看他們的學(xué)號(hào)是否相同就行了
也就是我們應(yīng)該比較能唯一標(biāo)識(shí)這個(gè)對(duì)象的一個(gè)甚至多個(gè)對(duì)象屬性,情況完全視不同對(duì)象而定
如果 A 未重寫 equals()如果 A 未重寫時(shí),調(diào)用的是父類的 equals(),還未重寫,會(huì)檢查到 Object,而 Object 是如下比較的
public boolean equals(Object obj) { return (this == obj); }
利用 == 號(hào)比較對(duì)象內(nèi)容是否相等未必有點(diǎn)草率,因此我們對(duì)這個(gè)方法應(yīng)當(dāng)十分謹(jǐn)慎
如何重寫重寫時(shí)需注意應(yīng)當(dāng)滿足如下規(guī)則,摘自 《Effective Java》
自反性:x.equals(x)必須返回true
對(duì)稱性:x.equals(y)與y.equals(x)的返回值必須相等
傳遞性:x.equals(y)為true,y.equals(z)也為true,那么x.equals(z)必須為true
一致性:如果對(duì)象x和y在equals()中使用的信息都沒有改變,那么x.equals(y)值始終不變
非null:x不是null,y為null,則x.equals(y)必須為false
在這里建議按以下規(guī)則重寫
建議判斷 a == b,省去沒必要的比較
建議先判斷 b instanceOf A,再做能能標(biāo)識(shí)唯一對(duì)象的一個(gè)或多個(gè)屬性的比較
建議考慮 super.equals(b)
a.hashCode()該方法返回的是對(duì)象的哈希值,主要應(yīng)用于哈希容器映射時(shí),將所有類型對(duì)象映射成整數(shù)
如何重寫在這里建議按以下規(guī)則重寫
建議對(duì)能標(biāo)識(shí)唯一對(duì)象的一個(gè)或多個(gè)屬性進(jìn)行 hashCode() 重寫
建議利用 jdk 基礎(chǔ)封裝類的 hashCode()
建議考慮 super.equals(b)
文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請(qǐng)注明本文地址:http://specialneedsforspecialkids.com/yun/67541.html
閱讀原文:不同時(shí)重寫equals和hashCode又怎樣! 可能一問到equals和hashCode相關(guān)的問題,就會(huì)有人講他們的自反性,對(duì)稱性,一致性,傳遞性等幾條約定了,此時(shí)我不得不佩服,這么多約定竟然都能記得,但我不知道你是不是真的理解呢。 我不同時(shí)重寫又能如何呢? showImg(https://segmentfault.com/img/remote/1460000018795219); 我...
摘要:而這次在一的一方實(shí)體里重寫基類的和方法做去重,感覺用的代碼量減少了,又能提高效率,所以我這里對(duì)這兩個(gè)方法做些自己的理解。不相等的兩個(gè)對(duì)象,不一定不相等。不相等,那么是一定不等的。文章若有錯(cuò)誤之處,歡迎指出。 昨天寫hibernate一對(duì)多查詢的時(shí)候,用set集合來儲(chǔ)存值,我們都知道java中List集合是有序,可重復(fù)的,Set集合是無序,不可重復(fù)的。所以當(dāng)時(shí)寫這個(gè)查詢的時(shí)候果斷用Set...
摘要:無論在中出現(xiàn)什么,都可以認(rèn)為它是對(duì)象除了八大基本數(shù)據(jù)類型。讓當(dāng)前線程等待某個(gè)對(duì)象的鎖,當(dāng)然應(yīng)該通過這個(gè)對(duì)象來操作了。但是要注意的是方法調(diào)用后,被喚醒的線程不會(huì)立馬獲得到鎖對(duì)象。主要的區(qū)別在于在釋放同時(shí),釋放了對(duì)象鎖的控制。 前言 五一回家又?jǐn)喔艘粋€(gè)放假時(shí)間了~~~ 只有光頭才能變強(qiáng) 回顧前面: ThreadLocal就是這么簡單 多線程三分鐘就可以入個(gè)門了! 多線程基礎(chǔ)必要知識(shí)點(diǎn)!...
摘要:語言通過字節(jié)碼的方式,在一定程度上解決了傳統(tǒng)解釋型語言執(zhí)行效率低的問題,同時(shí)又保留了解釋型語言可移植的特點(diǎn)。有針對(duì)不同系統(tǒng)的特定實(shí)現(xiàn),,,目的是使用相同的字節(jié)碼,它們都會(huì)給出相同的結(jié)果。項(xiàng)目主要基于捐贈(zèng)的源代碼。 本文來自于我的慕課網(wǎng)手記:Java編程中那些再熟悉不過的知識(shí)點(diǎn),轉(zhuǎn)載請(qǐng)保留鏈接 ;) 1. 面向?qū)ο蠛兔嫦蜻^程的區(qū)別 面向過程 優(yōu)點(diǎn): 性能比面向?qū)ο蟾摺R驗(yàn)轭愓{(diào)用時(shí)需要實(shí)例...
摘要:根據(jù)的重新計(jì)算值。如果這兩個(gè)的通過比較返回,新添加的將覆蓋集合中原有的,但不會(huì)覆蓋。如果這兩個(gè)的通過比較返回,新添加的將與集合中原有形成鏈,而且新添加的位于鏈的頭部具體說明繼續(xù)看方法的說明。 關(guān)于hashCode hashCode的存在主要是用于查找的快捷性,如Hashtable,HashMap等,hashCode是用來在散列存儲(chǔ)結(jié)構(gòu)中確定對(duì)象的存儲(chǔ)地址的. 1.hashcode是用來...
閱讀 3400·2021-11-24 10:30
閱讀 3269·2021-11-22 15:29
閱讀 3706·2021-10-28 09:32
閱讀 1254·2021-09-07 10:22
閱讀 3336·2019-08-30 15:55
閱讀 3619·2019-08-30 15:54
閱讀 3494·2019-08-30 15:54
閱讀 2833·2019-08-30 15:44