天天看點

Set

什麼是set

Set 具有與 Collection 完全一樣的接口 行為上不同 Set 不儲存重複的元素

分類

  1. HashSet:最主要的實作類 線程不安全 可以存儲null
  2. LinkedHashSet:作為HashSet子類 周遊内部資料時 可以按照添加的方式來顯示
  3. TreeSet:可以按照添加對象的指定屬性 進行排序

Set特點

  • 無序:存儲的資料在底層中并非按照資料的索引 而是根據資料的哈希值來确定位置
  • 不可重複:保證添加的元素按照equals判斷時 不能傳回true 即相同的元素隻能添加一個
  • Set接口中沒有拓展Collection中的方法(
  • 向Set接口中添加資料時 其所在的類一定要重寫 hashCode() 和 equals()方法 相等的對象必須擁有相等的散列碼

HashSet添加元素過程

向HashSet添加 元素 a 首先調用a所在類的hashCode()方法 計算a的哈希值
此哈希值通過HashSet内部某種算法計算出 a  在HashSet中的位置(即為 索引位置)
判斷此位置上是否有值
		如果沒有 元素 a 添加成功   ==>情況1
		如果存在元素 b(或者以連結清單存在的多個元素) 則比較元素 a 和 元素 b 的hash值
				如果不相同 添加成功	==>情況2
				如果相同 調用元素 a 所在類的equals方法
						equals傳回true 添加失敗
						equals傳回false 添加成功	=>情況3
情況2和情況3 元素 a 和 已經存在指定索引位置的元素以連結清單的方式進行存儲
jdk8:原來的資料在數組中 指向元素 a
jdk7:a放到數組中 指向原來的資料

HashSet底層:  數組 + 連結清單
           

示例

HashSet

package com.collection;


import org.junit.Test;

import java.util.HashSet;
import java.util.Set;

/*
* Set接口
* 無序 不可重複
* 無序:存儲的資料在底層中并非按照資料的索引 而是根據資料的哈希值來确定位置
* 不可重複:保證添加的元素按照equals判斷時 不能傳回true  即相同的元素隻能添加一個
* Set接口中沒有拓展Collection中的方法
* */
public class Demo03 {

    @Test
    public void test(){
        Set set = new HashSet();
        set.add(111);
        set.add(222);
        set.add(333);
        set.add(111);
        set.add(new User("yyll",20));
        set.add(new User("yyll",20));
        System.out.println(set);
        /*
        * 輸出結果 [333, 222, 111]
        * 不可重複
        * */
    }
}
           

TreeSet

package com.collection;

import org.junit.Test;

import java.util.TreeSet;

public class Demo04 {

    @Test
    public void test(){
        TreeSet treeSet = new TreeSet();
        treeSet.add(123);
        treeSet.add(445);
        treeSet.add(1323);
        treeSet.add("bb");
        /*
        * java.lang.Integer cannot be cast to java.lang.String
        *
        * 不能添加不同類型的資料
        * TreeSet
        * */
    }
}
           

小結

  1. Set接口

    無序

    不可重複

  2. TreeSet

    不能添加不同類型的資料 可以自定義排序規則

即使再小的帆也能遠航