2017-09-03 150 views
-3

我有這個問題很長一段時間。Java集合框架的內部工作

問題有點長。請耐心等待:)

總之,如何收集數據結構,如TreeSet知道它存儲的基礎數據何時被修改,以及它如何管理這些情況?

//Simple person class with name data member 
public static class Person { 
    String name; 

    public Person(String name) { 
     this.name = name; 
    } 
} 


1.創建一個TreeSet並添加3 Person實例P1,P2,P3。 (比較器排序名稱)。

TreeSet<Person> set = new TreeSet<>(new Comparator<Person>() { 
    @Override 
    public int compare(Person person1, Person person2) { 
     return person1.name.compareTo(person2.name); 
    } 
}); 

// Creating 3 Person instances and adding to set. 
Person p1 = new Person("Zach"), 
     p2 = new Person("Henry"), 
     p3 = new Person("Adam"); 

// Adding to set 
set.add(p1); set.add(p2); set.add(p3); 


2.打印的第一個元素(打印在平衡BST的辭書最小的字符串)

// This will name of P3 instance, i.e. Adam (obvious and expected) 
System.out.println(set.first().name); 
// "Adam" is printed which is expected. 


3.修改Person實例P3有 「斑馬」名稱。即亞當 - >斑馬

p3.name = "Zebra"; 

System.out.println(set.first().name); 


QUESTION
在第3節,我修改p3實例來保存 「斑馬」 而不是 「亞當」。
問題是,TreeSet如何知道P3實例已被修改?

TreeSet是使用一些平衡BST(通常是RB樹)構建的。因此,當我改變一些數據時,它必須重新排序樹的內部節點以保持遵守比較器的規則。
那麼,TreeSet是如何得到通知,底層數據已被修改,並且它必須重新排列樹節點?

我真的很想知道它是如何在內部工作的。它是觀察者模式嗎? 請求有點詳細和全面的解答:)

+2

你看過源代碼嗎?它很容易找到 - 是不是你應該首先看的地方? –

+1

我已經運行了你的測試,它不打印亨利。它按照我的預期打印斑馬紋。只需運行自己的測試就可以給出答案:它不知道有關更改,在將對象存儲在Set中後,更改對象的狀態是很重要的。 –

+0

[Stack Overflow用戶需要多少研究工作?](https://meta.stackoverflow.com/questions/261592/how-much-research-effort-is-expected-of-stack-overflow-users)答案,*「很多,一個荒謬的數額,超過你認爲你的能力,當你到達繩索的盡頭,並且沒有答案的痛苦超過了通過發佈你的問題收到的大量恥辱,那就是當你可以繼續詢問時。「* **看看源代碼將花費的時間少於編寫這個問題!** –

回答

0

如何收集數據結構,如TreeMap的知道什麼時候 底層數據IT賣場被修改,它是如何管理這樣的 情況?

它沒有。對於數值無關緊要,但如果您修改鍵值,則可能會損壞整個集合。這就是爲什麼你應該更喜歡地圖的不可變鍵,或者至少確保它們在被用作鍵後不會被修改。

還要注意TreeSetTreeMap支持,並HashSetHashMap支持,因此與他們同去(與設定值是地圖鍵)。

+0

問題中存在錯別字。它的TreeSet不是TreeMap ... – oathkeeper

+2

@oathkeeper TreeSet是一個TreeMap,其中所有條目的值始終是相同的值。 –