1. 程式人生 > >java容易被人忽略的細節

java容易被人忽略的細節

  1. 同一個類的雜湊值相等嗎?
  2. 字串的雜湊值相等嗎?
  3. 直接列印物件是個什麼東西?
  4. equals和== , ===

1.同一個類的雜湊值相等嗎?

我們用程式碼來測試一下,我們先來建立一個Person物件,裡面什麼屬性都沒有

public class Person{}

然後我們用這個類來生成小明和小芳,看一下他們的雜湊值

public class Test{
	public static void main(String[] args) {
		Person xiaoMing = new Person();
		Person xiaoFang =
new Person(); System.out.println("小明的雜湊值為"+xiaoMing.hashCode()+",小芳的雜湊值為:"+xiaoFang.hashCode()); System.out.println(); } }

在這裡插入圖片描述

結論:同一個類的雜湊值不一定相等,同一個物件的雜湊值才相等

2.字串的雜湊值相等嗎?

public static void main(String[] args) {
		String a=new String("a");
		String a2=new String("a");
		System.out.println
("a的雜湊值:"+a.hashCode()+",a2的雜湊值:"+a2.hashCode()); }

在這裡插入圖片描述
其實字串的雜湊值總是相等的,即便是通過new 的方式來進行建立
為什麼呢?
三臉茫然

因為String是一個特殊的類,java的對String的hashCode的方法早就寫好了。

3.直接列印物件是個什麼東西?

public static void main(String[] args) {
		Person xiaoMing = new Person();
		Person xiaoFang = new Person();
		System.out.println("直接列印小明:"
+xiaoMing+",直接列印小芳:"+xiaoFang); System.out.println(); }

在這裡插入圖片描述
三臉茫然
列印類,其實是呼叫類的toString方法,如果沒有重寫toString方法,則預設為:類的全路徑名@雜湊值,但仔細一看好像也不對啊,雜湊值還有數字,其實這個數字是16進位制的數字,不信我們來驗證一下。
三臉茫然
如果我們想列印物件時輸出一句話,那麼就得重新toString方法如下

public class Person{
	@Override
	public String toString() {
		return "我是一個人";
	}
}
public static void main(String[] args) {
		System.out.println(new Person());
	}

在這裡插入圖片描述

4.equals和== , ===

咱們還是拿Person過來做例子,給這個Person一個屬性name

public class Person{
	private String name;
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
	public Person(String name){
		this.name=name;
	}
}

再來測試

public static void main(String[] args) {
		Person xiaoMing = new Person("小明");
		Person xiaoMing2 = new Person("小明");
		System.out.println(xiaoMing==xiaoMing2);
	}

結果是false,==比較的是他們在記憶體中的存放位置的地址值的,所以當然不相等了。那怎麼樣才能讓他們按照名字相等給我返回true呢?
答案就是使用equals方法,我們需要在類裡面重寫這個equals方法。

public class Person{
	private String name;
	public String getName() {
		return name;
	}
	public Person(String name){
		this.name=name;
	}
	public void setName(String name) {
		this.name = name;
	}
	public boolean equals(Person obj) {
		return obj.getName()==this.name;
	}
}
	public static void main(String[] args) {
		Person xiaoMing = new Person("小明");
		Person xiaoMing2 = new Person("小明");
		System.out.println(xiaoMing.equals(xiaoMing2));
	}

這個時候返回的就是true。
但是在equals方法裡注意到我用了==符號,這裡沒問題嗎?String型別還有特權嗎?猜猜看

	public static void main(String[] args) {
		System.out.println("a"=="a");
		System.out.println(new String("a")=="a");
		System.out.println(new String("a")==new String("a"));
	}

在這裡插入圖片描述
驚不驚喜,意不意外
字串是還真的比較特殊,因為java會在內容中為String型別的對像開闢一個空間,稱為串池,字串物件的建立之後會被放入到串池中,對於相同物件,池中只儲存一份。串池會把"a" 對於這樣的型別的宣告方式(不是new出來的)串池把他們看做一個物件,所以池中只儲存一分,故相等!
對於String只要用new關鍵字new出來的string,都是單獨的一個物件。
而== 號他是用來比較物件的記憶體地址的,只要不是自己比自己,那肯定是false。

我的GitHub
QQ:2541692705
郵箱:[email protected]
我想去流浪,我想去讀書,若有機會,江湖再見
掃一掃,領取紅包,就當獎勵你我付出的努力