java 集合框架(1)

一. 概述

java集合是java提供的工具包,包含了常用的數(shù)據(jù)結(jié)構(gòu),如集合,鏈表,隊(duì)列,棧,數(shù)組,映射等。
java集合工具包的位置是java.util.*
下面是java集合框架圖:

Java集合框架.gif

說(shuō)明

  • 點(diǎn)線框表示接口
  • 虛線框表示抽象類
  • 實(shí)線框代表普通(實(shí)際)類。
  • 點(diǎn)線箭頭表示一個(gè)特定的類準(zhǔn)備實(shí)現(xiàn)一個(gè)接口。
  • 雙線箭頭表示一個(gè)類可生成箭頭指向的那個(gè)類的對(duì)象。例如,任何集合都可以生成一個(gè)迭代器( Iterator),而一個(gè)列表可以生成一個(gè)ListIterator(以及原始的迭代器,因?yàn)榱斜硎菑募侠^承的)。

由于集合庫(kù)提供了足夠多的功能,我們不必要通過(guò)繼承抽象類來(lái)實(shí)現(xiàn)自己的集合,所以我們忽略框架圖中的抽象類,只需要關(guān)注最頂端的接口和實(shí)際類即可。

由此我們可以將java集合劃分為四個(gè)部分:

  1. Collection
    Collection是一個(gè)接口,是高度抽象出來(lái)的集合,它包含了集合的基本操作和屬性。
    Collection包含了List,Set和Queue。

(1)List
List是一個(gè)有序的隊(duì)列,每一個(gè)元素都有它的索引。第一個(gè)元素的索引值是0。
List的實(shí)現(xiàn)類有LinkedList, ArrayList, Vector, Stack。

(2)Set
Set是一個(gè)不允許有重復(fù)元素的集合。
Set的實(shí)現(xiàn)類有HastSet和TreeSet。HashSet依賴于HashMap,它實(shí)際上是通過(guò)HashMap實(shí)現(xiàn)的;TreeSet依賴于TreeMap,它實(shí)際上是通過(guò)TreeMap實(shí)現(xiàn)的。

(3)Queue
Queue(隊(duì)列)一種特殊的線性表,它只允許在表的前端進(jìn)行刪除操作,而在表的后端進(jìn)行插入操作。

  1. Map
    Map是一個(gè)映射接口,即key-value鍵值對(duì)。Map中的每一個(gè)元素包含“一個(gè)key”和“key對(duì)應(yīng)的value”。
  2. 工具類
    (1)Iterator
    遍歷集合的工具
    (2)Enumeration
    (3)Arrays
    (4)Collections

有了上面的整體框架之后,我們接下來(lái)對(duì)每個(gè)類分別進(jìn)行分析。


二. Collection

Collection接口是處理對(duì)象集合的根接口,其中定義了很多對(duì)元素進(jìn)行操作的方法,下圖展示了Collection的全部方法:

Collection.png

部分方法說(shuō)明

  • boolean isEmpty() 若集合內(nèi)沒(méi)有元素,就返回“真”
  • int size() 返回集合內(nèi)的元素?cái)?shù)量
  • boolean contains(Object) 若集合包含自變量,就返回“真”
  • Iterator iterator() 返回一個(gè)迭代器,以用它遍歷集合的各元素
  • Object[] toArray() 返回包含了集合內(nèi)所有元素的一個(gè)數(shù)組

2.1 List

順序是 List 最重要的特性;它可保證元素按照規(guī)定的順序排列。
List 為 Collection 添加了大量方法,以便我們?cè)?List 中部插入和刪除元素(只推薦對(duì) LinkedList 這樣做)。
List 也會(huì)生成一個(gè)ListIterator(列表反復(fù)器),利用它可在一個(gè)列表里朝兩個(gè)方向遍歷,同時(shí)插入和刪除位于列表中部的元素(同樣地,只建議對(duì) LinkedList 這樣做)。
下面介紹List接口的兩個(gè)重要的具體實(shí)現(xiàn)類,也是我們可能最常用的類,ArrayList和LinkedList。

ArrayList
  • ArrayList 實(shí)際上是通過(guò)一個(gè)數(shù)組去保存數(shù)據(jù)的。當(dāng)我們構(gòu)造ArrayList時(shí);若使用默認(rèn)構(gòu)造函數(shù),則ArrayList的默認(rèn)容量大小是10。
  • 當(dāng)ArrayList容量不足以容納全部元素時(shí),ArrayList會(huì)重新設(shè)置容量:新的容量=“(原始容量x3)/2 + 1”。
  • 和Vector不同,ArrayList中的操作不是線程安全的!所以,建議在單線程中才使用ArrayList,而在多線程中可以選擇Vector
  1. ArrayList構(gòu)造函數(shù)
// 默認(rèn)構(gòu)造函數(shù)
ArrayList()

// capacity是ArrayList的默認(rèn)容量大小。當(dāng)由于增加數(shù)據(jù)導(dǎo)致容量不足時(shí),容量會(huì)添加上一次容量大小的一半。
ArrayList(int capacity)

// 創(chuàng)建一個(gè)包含collection的ArrayList
ArrayList(Collection<? extends E> collection)
  1. ArrayList API
// Collection中定義的API
boolean             add(E object)
boolean             addAll(Collection<? extends E> collection)
void                clear()
boolean             contains(Object object)
boolean             containsAll(Collection<?> collection)
boolean             equals(Object object)
int                 hashCode()
boolean             isEmpty()
Iterator<E>         iterator()
boolean             remove(Object object)
boolean             removeAll(Collection<?> collection)
boolean             retainAll(Collection<?> collection)
int                 size()
<T> T[]             toArray(T[] array)
Object[]            toArray()
// AbstractCollection中定義的API
void                add(int location, E object)
boolean             addAll(int location, Collection<? extends E> collection)
E                   get(int location)
int                 indexOf(Object object)
int                 lastIndexOf(Object object)
ListIterator<E>     listIterator(int location)
ListIterator<E>     listIterator()
E                   remove(int location)
E                   set(int location, E object)
List<E>             subList(int start, int end)
// ArrayList新增的API
Object               clone()
void                 ensureCapacity(int minimumCapacity)
void                 trimToSize()
void                 removeRange(int fromIndex, int toIndex)
  1. ArrayList遍歷方式
    ArrayList支持3種遍歷方式
  • 第一種,通過(guò)迭代器遍歷。即通過(guò)Iterator去遍歷。
Integer value = null;
Iterator iter = list.iterator();
while (iter.hasNext()) {
    value = (Integer)iter.next();
}
  • 第二種,隨機(jī)訪問(wèn),通過(guò)索引值去遍歷。
    由于ArrayList實(shí)現(xiàn)了RandomAccess接口,它支持通過(guò)索引值去隨機(jī)訪問(wèn)元素。
Integer value = null;
int size = list.size();
for (int i=0; i<size; i++) {
    value = (Integer)list.get(i);        
}
  • 第三種,for循環(huán)遍歷。如下:
Integer value = null;
for (Integer integ:list) {
    value = integ;
}

PS: 遍歷ArrayList時(shí),使用隨機(jī)訪問(wèn)(即,通過(guò)索引序號(hào)訪問(wèn))效率最高,而使用迭代器的效率最低!

  1. 示例
import java.util.*;

/*
 * @desc ArrayList常用API的測(cè)試程序
 * @author skywang 
 * @email kuiwu-wang@163.com
 */
public class ArrayListTest {

    public static void main(String[] args) {
        
        // 創(chuàng)建ArrayList
        ArrayList list = new ArrayList();

        // 將“”
        list.add("1");
        list.add("2");
        list.add("3");
        list.add("4");
        // 將下面的元素添加到第1個(gè)位置
        list.add(0, "5");

        // 獲取第1個(gè)元素
        System.out.println("the first element is: "+ list.get(0));
        // 刪除“3”
        list.remove("3");
        // 獲取ArrayList的大小
        System.out.println("Arraylist size=: "+ list.size());
        // 判斷l(xiāng)ist中是否包含"3"
        System.out.println("ArrayList contains 3 is: "+ list.contains(3));
        // 設(shè)置第2個(gè)元素為10
        list.set(1, "10");

        // 通過(guò)Iterator遍歷ArrayList
        for(Iterator iter = list.iterator(); iter.hasNext(); ) {
            System.out.println("next is: "+ iter.next());
        }

        // 將ArrayList轉(zhuǎn)換為數(shù)組
        String[] arr = (String[])list.toArray(new String[0]);
        for (String str:arr)
            System.out.println("str: "+ str);

        // 清空ArrayList
        list.clear();
        // 判斷ArrayList是否為空
        System.out.println("ArrayList is empty: "+ list.isEmpty());
    }
}

運(yùn)行結(jié)果

the first element is: 5
Arraylist size=: 4
ArrayList contains 3 is: false
next is: 5
next is: 10
next is: 2
next is: 4
str: 5
str: 10
str: 2
str: 4
ArrayList is empty: true

LinkedList
  • LinkedList實(shí)際上是通過(guò)雙向鏈表去實(shí)現(xiàn)的。它的順序訪問(wèn)會(huì)非常高效,而隨機(jī)訪問(wèn)效率比較低。
  • 它包含一個(gè)非常重要的內(nèi)部類:Entry。Entry是雙向鏈表節(jié)點(diǎn)所對(duì)應(yīng)的數(shù)據(jù)結(jié)構(gòu),它包括的屬性有:當(dāng)前節(jié)點(diǎn)所包含的值,上一個(gè)節(jié)點(diǎn),下一個(gè)節(jié)點(diǎn)。
  1. LinkedList API
LinkedList的API
boolean       add(E object)
void          add(int location, E object)
boolean       addAll(Collection<? extends E> collection)
boolean       addAll(int location, Collection<? extends E> collection)
void          addFirst(E object)
void          addLast(E object)
void          clear()
Object        clone()
boolean       contains(Object object)
Iterator<E>   descendingIterator()
E             element()
E             get(int location)
E             getFirst()
E             getLast()
int           indexOf(Object object)
int           lastIndexOf(Object object)
ListIterator<E>     listIterator(int location)
boolean       offer(E o)
boolean       offerFirst(E e)
boolean       offerLast(E e)
E             peek()
E             peekFirst()
E             peekLast()
E             poll()
E             pollFirst()
E             pollLast()
E             pop()
void          push(E e)
E             remove()
E             remove(int location)
boolean       remove(Object object)
E             removeFirst()
boolean       removeFirstOccurrence(Object o)
E             removeLast()
boolean       removeLastOccurrence(Object o)
E             set(int location, E object)
int           size()
<T> T[]       toArray(T[] contents)
Object[]     toArray()
  1. LinkedList遍歷方式
  • 通過(guò)迭代器遍歷。即通過(guò)Iterator去遍歷。
for(Iterator iter = list.iterator(); iter.hasNext();)
    iter.next();
  • 通過(guò)另外一種for循環(huán)來(lái)遍歷LinkedList
for (Integer integ:list) 
    ;

PS1: 使用for循環(huán)的效率較使用迭代器高
PS2: 無(wú)論如何,千萬(wàn)不要通過(guò)隨機(jī)訪問(wèn)去遍歷LinkedList!

  1. 示例
import java.util.List;
import java.util.Iterator;
import java.util.LinkedList;
import java.util.NoSuchElementException;

public class LinkedListTest {
    public static void main(String[] args) {
        // 測(cè)試LinkedList的API
        testLinkedListAPIs() ;

        // 將LinkedList當(dāng)作 LIFO(后進(jìn)先出)的堆棧
        useLinkedListAsLIFO();

        // 將LinkedList當(dāng)作 FIFO(先進(jìn)先出)的隊(duì)列
        useLinkedListAsFIFO();
    }
    
    /*
     * 測(cè)試LinkedList中部分API
     */
    private static void testLinkedListAPIs() {
        String val = null;
        // 新建一個(gè)LinkedList
        LinkedList llist = new LinkedList();
        //---- 添加操作 ----
        // 依次添加1,2,3
        llist.add("1");
        llist.add("2");
        llist.add("3");

        // 將“4”添加到第一個(gè)位置
        llist.add(1, "4");
        

        System.out.println("\nTest \"addFirst(), removeFirst(), getFirst()\"");
        // (01) 將“10”添加到第一個(gè)位置。  失敗的話,拋出異常!
        llist.addFirst("10");
        System.out.println("llist:"+llist);
        // (02) 將第一個(gè)元素刪除。        失敗的話,拋出異常!
        System.out.println("llist.removeFirst():"+llist.removeFirst());
        System.out.println("llist:"+llist);
        // (03) 獲取第一個(gè)元素。          失敗的話,拋出異常!
        System.out.println("llist.getFirst():"+llist.getFirst());


        System.out.println("\nTest \"offerFirst(), pollFirst(), peekFirst()\"");
        // (01) 將“10”添加到第一個(gè)位置。  返回true。
        llist.offerFirst("10");
        System.out.println("llist:"+llist);
        // (02) 將第一個(gè)元素刪除。        失敗的話,返回null。
        System.out.println("llist.pollFirst():"+llist.pollFirst());
        System.out.println("llist:"+llist);
        // (03) 獲取第一個(gè)元素。          失敗的話,返回null。
        System.out.println("llist.peekFirst():"+llist.peekFirst());
    

        System.out.println("\nTest \"addLast(), removeLast(), getLast()\"");
        // (01) 將“20”添加到最后一個(gè)位置。  失敗的話,拋出異常!
        llist.addLast("20");
        System.out.println("llist:"+llist);
        // (02) 將最后一個(gè)元素刪除。        失敗的話,拋出異常!
        System.out.println("llist.removeLast():"+llist.removeLast());
        System.out.println("llist:"+llist);
        // (03) 獲取最后一個(gè)元素。          失敗的話,拋出異常!
        System.out.println("llist.getLast():"+llist.getLast());


        System.out.println("\nTest \"offerLast(), pollLast(), peekLast()\"");
        // (01) 將“20”添加到第一個(gè)位置。  返回true。
        llist.offerLast("20");
        System.out.println("llist:"+llist);
        // (02) 將第一個(gè)元素刪除。        失敗的話,返回null。
        System.out.println("llist.pollLast():"+llist.pollLast());
        System.out.println("llist:"+llist);
        // (03) 獲取第一個(gè)元素。          失敗的話,返回null。
        System.out.println("llist.peekLast():"+llist.peekLast());

         

        // 將第3個(gè)元素設(shè)置300。不建議在LinkedList中使用此操作,因?yàn)樾实停?        llist.set(2, "300");
        // 獲取第3個(gè)元素。不建議在LinkedList中使用此操作,因?yàn)樾实停?        System.out.println("\nget(3):"+llist.get(2));


        // ---- toArray(T[] a) ----
        // 將LinkedList轉(zhuǎn)行為數(shù)組
        String[] arr = (String[])llist.toArray(new String[0]);
        for (String str:arr) 
            System.out.println("str:"+str);

        // 輸出大小
        System.out.println("size:"+llist.size());
        // 清空LinkedList
        llist.clear();
        // 判斷LinkedList是否為空
        System.out.println("isEmpty():"+llist.isEmpty()+"\n");

    }

    /**
     * 將LinkedList當(dāng)作 LIFO(后進(jìn)先出)的堆棧
     */
    private static void useLinkedListAsLIFO() {
        System.out.println("\nuseLinkedListAsLIFO");
        // 新建一個(gè)LinkedList
        LinkedList stack = new LinkedList();

        // 將1,2,3,4添加到堆棧中
        stack.push("1");
        stack.push("2");
        stack.push("3");
        stack.push("4");
        // 打印“?!?        System.out.println("stack:"+stack);

        // 刪除“棧頂元素”
        System.out.println("stack.pop():"+stack.pop());
        
        // 取出“棧頂元素”
        System.out.println("stack.peek():"+stack.peek());

        // 打印“?!?        System.out.println("stack:"+stack);
    }

    /**
     * 將LinkedList當(dāng)作 FIFO(先進(jìn)先出)的隊(duì)列
     */
    private static void useLinkedListAsFIFO() {
        System.out.println("\nuseLinkedListAsFIFO");
        // 新建一個(gè)LinkedList
        LinkedList queue = new LinkedList();

        // 將10,20,30,40添加到隊(duì)列。每次都是插入到末尾
        queue.add("10");
        queue.add("20");
        queue.add("30");
        queue.add("40");
        // 打印“隊(duì)列”
        System.out.println("queue:"+queue);

        // 刪除(隊(duì)列的第一個(gè)元素)
        System.out.println("queue.remove():"+queue.remove());
    
        // 讀取(隊(duì)列的第一個(gè)元素)
        System.out.println("queue.element():"+queue.element());

        // 打印“隊(duì)列”
        System.out.println("queue:"+queue);
    }
}

運(yùn)行結(jié)果

Test "addFirst(), removeFirst(), getFirst()"
llist:[10, 1, 4, 2, 3]
llist.removeFirst():10
llist:[1, 4, 2, 3]
llist.getFirst():1

Test "offerFirst(), pollFirst(), peekFirst()"
llist:[10, 1, 4, 2, 3]
llist.pollFirst():10
llist:[1, 4, 2, 3]
llist.peekFirst():1

Test "addLast(), removeLast(), getLast()"
llist:[1, 4, 2, 3, 20]
llist.removeLast():20
llist:[1, 4, 2, 3]
llist.getLast():3

Test "offerLast(), pollLast(), peekLast()"
llist:[1, 4, 2, 3, 20]
llist.pollLast():20
llist:[1, 4, 2, 3]
llist.peekLast():3

get(3):300
str:1
str:4
str:300
str:3
size:4
isEmpty():true


useLinkedListAsLIFO
stack:[4, 3, 2, 1]
stack.pop():4
stack.peek():3
stack:[3, 2, 1]

useLinkedListAsFIFO
queue:[10, 20, 30, 40]
queue.remove():10
queue.element():20
queue:[20, 30, 40]

實(shí)際使用中我們需要根據(jù)特定的需求選用合適的類,如果除了在末尾外不能在其他位置插入或者刪除元素,那么ArrayList效率更高,如果需要經(jīng)常插入或者刪除元素,就選擇LinkedList。


2.2 Set

  • Set 是繼承于Collection的接口。它是一個(gè)不允許有重復(fù)元素的集合。
  • HastSet 和 TreeSet 是Set的兩個(gè)實(shí)現(xiàn)類。
  • HashSet依賴于HashMap,它實(shí)際上是通過(guò)HashMap實(shí)現(xiàn)的。HashSet中的元素是無(wú)序的。
  • TreeSet依賴于TreeMap,它實(shí)際上是通過(guò)TreeMap實(shí)現(xiàn)的。TreeSet中的元素是有序的。
HashSet

HashSet 是一個(gè)沒(méi)有重復(fù)元素的集合。

  1. HashSet API
boolean         add(E object)
void            clear()
Object          clone()
boolean         contains(Object object)
boolean         isEmpty()
Iterator<E>     iterator()
boolean         remove(Object object)
int             size()
  1. HashSet遍歷方式
  • 通過(guò)Iterator遍歷HashSet(推薦)
for(Iterator iterator = set.iterator();iterator.hasNext(); ) { 
    iterator.next();
}   
  • 通過(guò)for-each遍歷HashSet
String[] arr = (String[])set.toArray(new String[0]);
for (String str:arr)
    System.out.printf("for each : %s\n", str);

HashSet遍歷測(cè)試程序如下:

import java.util.Random;
import java.util.Iterator;
import java.util.HashSet;

/*
 * @desc 介紹HashSet遍歷方法
 */
public class HashSetIteratorTest {

    public static void main(String[] args) {
        // 新建HashSet
        HashSet set = new HashSet();

        // 添加元素 到HashSet中
        for (int i=0; i<5; i++)
            set.add(""+i);

        // 通過(guò)Iterator遍歷HashSet
        iteratorHashSet(set) ;

        // 通過(guò)for-each遍歷HashSet
        foreachHashSet(set);
    }

    /*
     * 通過(guò)Iterator遍歷HashSet。推薦方式
     */
    private static void iteratorHashSet(HashSet set) {
        for(Iterator iterator = set.iterator();
               iterator.hasNext(); ) {
            System.out.printf("iterator : %s\n", iterator.next());
        }
    }

    /*
     * 通過(guò)for-each遍歷HashSet。不推薦!此方法需要先將Set轉(zhuǎn)換為數(shù)組
     */
    private static void foreachHashSet(HashSet set) {
        String[] arr = (String[])set.toArray(new String[0]);
        for (String str:arr)
            System.out.printf("for each : %s\n", str);
    }
}

運(yùn)行結(jié)果:

iterator : 3
iterator : 2
iterator : 1
iterator : 0
iterator : 4
for each : 3
for each : 2
for each : 1
for each : 0
for each : 4
  1. 示例
import java.util.Iterator;
import java.util.HashSet;

/*
 * @desc HashSet常用API的使用。
 */
public class HashSetTest {

    public static void main(String[] args) {
        // HashSet常用API
        testHashSetAPIs() ;
    }

    /*
     * HashSet除了iterator()和add()之外的其它常用API
     */
    private static void testHashSetAPIs() {
        // 新建HashSet
        HashSet set = new HashSet();

        // 將元素添加到Set中
        set.add("a");
        set.add("b");
        set.add("c");
        set.add("d");
        set.add("e");

        // 打印HashSet的實(shí)際大小
        System.out.printf("size : %d\n", set.size());

        // 判斷HashSet是否包含某個(gè)值
        System.out.printf("HashSet contains a :%s\n", set.contains("a"));
        System.out.printf("HashSet contains g :%s\n", set.contains("g"));

        // 刪除HashSet中的“e”
        set.remove("e");

        // 將Set轉(zhuǎn)換為數(shù)組
        String[] arr = (String[])set.toArray(new String[0]);
        for (String str:arr)
            System.out.printf("for each : %s\n", str);

        // 新建一個(gè)包含b、c、f的HashSet
        HashSet otherset = new HashSet();
        otherset.add("b");
        otherset.add("c");
        otherset.add("f");

        // 克隆一個(gè)removeset,內(nèi)容和set一模一樣
        HashSet removeset = (HashSet)set.clone();
        // 刪除“removeset中,屬于otherSet的元素”
        removeset.removeAll(otherset);
        // 打印removeset
        System.out.printf("removeset : %s\n", removeset);

        // 克隆一個(gè)retainset,內(nèi)容和set一模一樣
        HashSet retainset = (HashSet)set.clone();
        // 保留“retainset中,屬于otherSet的元素”
        retainset.retainAll(otherset);
        // 打印retainset
        System.out.printf("retainset : %s\n", retainset);


        // 遍歷HashSet
        for(Iterator iterator = set.iterator();
               iterator.hasNext(); ) 
            System.out.printf("iterator : %s\n", iterator.next());

        // 清空HashSet
        set.clear();

        // 輸出HashSet是否為空
        System.out.printf("%s\n", set.isEmpty()?"set is empty":"set is not empty");
    }

}

運(yùn)行結(jié)果:

size : 5
HashSet contains a :true
HashSet contains g :false
for each : d
for each : b
for each : c
for each : a
removeset : [d, a]
retainset : [b, c]
iterator : d
iterator : b
iterator : c
iterator : a
set is empty

TreeSet
  • TreeSet 是一個(gè)有序的集合,它的作用是提供有序的Set集合。
  • TreeSet是非線程安全的。
  1. TreeSet API
boolean                   add(E object)
boolean                   addAll(Collection<? extends E> collection)
void                      clear()
Object                    clone()
boolean                   contains(Object object)
E                         first()
boolean                   isEmpty()
E                         last()
E                         pollFirst()
E                         pollLast()
E                         lower(E e)
E                         floor(E e)
E                         ceiling(E e)
E                         higher(E e)
boolean                   remove(Object object)
int                       size()
Comparator<? super E>     comparator()
Iterator<E>               iterator()
Iterator<E>               descendingIterator()
SortedSet<E>              headSet(E end)
NavigableSet<E>           descendingSet()
NavigableSet<E>           headSet(E end, boolean endInclusive)
SortedSet<E>              subSet(E start, E end)
NavigableSet<E>           subSet(E start, boolean startInclusive, E end, boolean endInclusive)
NavigableSet<E>           tailSet(E start, boolean startInclusive)
SortedSet<E>              tailSet(E start)
  • TreeSet是有序的Set集合,因此支持add、remove、get等方法。
  1. TreeSet遍歷方式
  • Iterator順序遍歷
for(Iterator iter = set.iterator(); iter.hasNext(); ) { 
    iter.next();
}   
  • for-each遍歷HashSet
// 假設(shè)set是TreeSet對(duì)象,并且set中元素是String類型
String[] arr = (String[])set.toArray(new String[0]);
for (String str:arr)
    System.out.printf("for each : %s\n", str);

TreeSet不支持快速隨機(jī)遍歷,只能通過(guò)迭代器進(jìn)行遍歷!

  1. 示例
import java.util.*;

/**
 * @desc TreeSet的API測(cè)試
 */
public class TreeSetTest {

    public static void main(String[] args) {
        testTreeSetAPIs();
    }
    
    // 測(cè)試TreeSet的api
    public static void testTreeSetAPIs() {
        String val;

        // 新建TreeSet
        TreeSet tSet = new TreeSet();
        // 將元素添加到TreeSet中
        tSet.add("aaa");
        // Set中不允許重復(fù)元素,所以只會(huì)保存一個(gè)“aaa”
        tSet.add("aaa");
        tSet.add("bbb");
        tSet.add("eee");
        tSet.add("ddd");
        tSet.add("ccc");
        System.out.println("TreeSet:"+tSet);

        // 打印TreeSet的實(shí)際大小
        System.out.printf("size : %d\n", tSet.size());

        // 導(dǎo)航方法
        // floor(小于、等于)
        System.out.printf("floor bbb: %s\n", tSet.floor("bbb"));
        // lower(小于)
        System.out.printf("lower bbb: %s\n", tSet.lower("bbb"));
        // ceiling(大于、等于)
        System.out.printf("ceiling bbb: %s\n", tSet.ceiling("bbb"));
        System.out.printf("ceiling eee: %s\n", tSet.ceiling("eee"));
        // ceiling(大于)
        System.out.printf("higher bbb: %s\n", tSet.higher("bbb"));
        // subSet()
        System.out.printf("subSet(aaa, true, ccc, true): %s\n", tSet.subSet("aaa", true, "ccc", true));
        System.out.printf("subSet(aaa, true, ccc, false): %s\n", tSet.subSet("aaa", true, "ccc", false));
        System.out.printf("subSet(aaa, false, ccc, true): %s\n", tSet.subSet("aaa", false, "ccc", true));
        System.out.printf("subSet(aaa, false, ccc, false): %s\n", tSet.subSet("aaa", false, "ccc", false));
        // headSet()
        System.out.printf("headSet(ccc, true): %s\n", tSet.headSet("ccc", true));
        System.out.printf("headSet(ccc, false): %s\n", tSet.headSet("ccc", false));
        // tailSet()
        System.out.printf("tailSet(ccc, true): %s\n", tSet.tailSet("ccc", true));
        System.out.printf("tailSet(ccc, false): %s\n", tSet.tailSet("ccc", false));


        // 刪除“ccc”
        tSet.remove("ccc");
        // 將Set轉(zhuǎn)換為數(shù)組
        String[] arr = (String[])tSet.toArray(new String[0]);
        for (String str:arr)
            System.out.printf("for each : %s\n", str);

        // 打印TreeSet
        System.out.printf("TreeSet:%s\n", tSet);

        // 遍歷TreeSet
        for(Iterator iter = tSet.iterator(); iter.hasNext(); ) {
            System.out.printf("iter : %s\n", iter.next());
        }

        // 刪除并返回第一個(gè)元素
        val = (String)tSet.pollFirst();
        System.out.printf("pollFirst=%s, set=%s\n", val, tSet);

        // 刪除并返回最后一個(gè)元素
        val = (String)tSet.pollLast();
        System.out.printf("pollLast=%s, set=%s\n", val, tSet);

        // 清空HashSet
        tSet.clear();

        // 輸出HashSet是否為空
        System.out.printf("%s\n", tSet.isEmpty()?"set is empty":"set is not empty");
    }
}

運(yùn)行結(jié)果:

TreeSet:[aaa, bbb, ccc, ddd, eee]
size : 5
floor bbb: bbb
lower bbb: aaa
ceiling bbb: bbb
ceiling eee: eee
higher bbb: ccc
subSet(aaa, true, ccc, true): [aaa, bbb, ccc]
subSet(aaa, true, ccc, false): [aaa, bbb]
subSet(aaa, false, ccc, true): [bbb, ccc]
subSet(aaa, false, ccc, false): [bbb]
headSet(ccc, true): [aaa, bbb, ccc]
headSet(ccc, false): [aaa, bbb]
tailSet(ccc, true): [ccc, ddd, eee]
tailSet(ccc, false): [ddd, eee]
for each : aaa
for each : bbb
for each : ddd
for each : eee
TreeSet:[aaa, bbb, ddd, eee]
iter : aaa
iter : bbb
iter : ddd
iter : eee
pollFirst=aaa, set=[bbb, ddd, eee]
pollLast=eee, set=[bbb, ddd]
set is empty
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • Java集合類可用于存儲(chǔ)數(shù)量不等的對(duì)象,并可以實(shí)現(xiàn)常用的數(shù)據(jù)結(jié)構(gòu)如棧,隊(duì)列等,Java集合還可以用于保存具有映射關(guān)...
    小徐andorid閱讀 2,079評(píng)論 0 13
  • 集合類框架的介紹: ![Java 集合類框架](https://upload-images.jianshu.io/...
    LynnGuo閱讀 799評(píng)論 0 1
  • 四、集合框架 1:String類:字符串(重點(diǎn)) (1)多個(gè)字符組成的一個(gè)序列,叫字符串。生活中很多數(shù)據(jù)的描述都采...
    佘大將軍閱讀 867評(píng)論 0 2
  • 在編程中,常常需要集中存放多個(gè)數(shù)據(jù)。集合類主要負(fù)責(zé)保存、盛裝其他數(shù)據(jù),因此集合類也被稱為容器類。所有的集合類都位于...
    一一一二二三閱讀 483評(píng)論 0 1
  • 原文地址 Java集合 Java集合框架:是一種工具類,就像是一個(gè)容器可以存儲(chǔ)任意數(shù)量的具有共同屬性的對(duì)象。 Ja...
    gyl_coder閱讀 1,034評(píng)論 0 8

友情鏈接更多精彩內(nèi)容