Set常用子類特點
HashSet: 重寫 hashCode和equals方法
特點:無序,唯一
底層結構是:
哈希表:元素為鏈表的數組。綜合了鏈表和數組的好處
add方法:底層實際是依賴於HashCode()和equals()方法
HashSet實際用的是HashMap
public HashSet() {
map = new HashMap<>();
}
案例-HashSet存儲自定義對象
出現問題:
重復的元素也被添加了,不能保證元素唯一性
原因:自定義類沒有重寫HashCode和equals方法;
分析:
(1) 默認繼承Object類的HashCode和equals方法,而Object的HashCode值是通過對象
的內部地址值轉換為一個整數得到的,不同的對象的地址值不同,進而可以知道轉換後
的HashCode值也不可能相同。HashCode值不同就當作不是重復的元素而添加了。
(2)equals方法默認也是比較地址值,如果不重寫equals方法,那麽不同的對象
比較的結果也一定就是false;將會當作不是重復元素而添加了
解決:重寫自定義類的HashCode和equals方法
思考:重寫HashCode(),那麽HashCode值跟什麽有關系呢?
答: 和對象的成員變量值有關系
重寫HashCode方法:
就將對象的成員變量值相加:
基本類型:直接相加
引用類型:就加哈希值
// return name.hashCode()+age;
// 代碼優化如下
return name.hashCode()+age*31;
註意:判斷是否是重復元素步驟:
1-先比較HashCode值:
1-1:如果HashCode值不同:直接添加
1-2:如果HashCode值相同:
1-2-1:繼續判斷equals方法:
返回false:添加元素
返回true:放棄添加
對於hashCode和equals方法的理解:(新華字典: 即使是在同一頁了,也有可能不是同一個元素)
同一頁:hashCode值
同一頁中同一個元素:hashCode值相同情況下,還要繼續采用equals方法判斷
二、LinkedHashSet:
底層數據結構是:鏈表和哈希表
鏈表保證元素有序
哈希表保證元素唯一
三、TreeSet:
(1)實現Comparable自然排序接口,重寫compareTo方法
(2)實現Comparator比較器排序接口,重寫compare方法
排序方式:以構造函數確定排序方式
A 無參構造:自然排序
class Student implements Comparable<Student>{
@Override
public int compareTo(Student s){
//按年齡排序
int num=this.age-s.age;
//隱含條件,年齡相同時,應該繼續比較姓名
int num2=num==0?this.name.compareTo(s.name):num;
return num2;
}
}
B 有參構造:比較器排序 將自定義的比較器類對象作為構造方法的參數
class MyComparator implements Comparator<Student>{
@Override
public int compare(Student s1,Student s2){
int num=(int)(stu2.getTotal()-stu1.getTotal());
int num2=num==0?stu1.getName().compareTo(stu2.getName()):num;
return num2;
}
}
TreeSet<Student> ts=new TreeSet<Student>(new MyComparator());
---------------------------------------------
字符串的比較
int compareTo(String str):
Set常用子類特點