思考爲何要引入容器這個概念?html
Java有多種方式保存對象(應該是對象的引用),例如使用數組時保存一組對象中的最有效的方式,若是你想保存一組基本類型的數據,也推薦使用這種方式,但你們知道數組是具備固定尺寸的,你必須事先知道你要須要多少個對象。可是在通常的狀況中,你在寫程序中並不知道將須要多少個對象,或者是否須要更加複雜的方式來存儲對象,所以數組尺寸固定很不爽!java
爲了解決上述問題,引入了容器的概念。容器提供了完善的方法來保存對象,你可使用這些工具來解決數量驚人的問題。Java容器類能夠自動調整本身的尺寸,所以與數組不一樣,你能夠將任意數量的對象放到容器中,並不擔憂容器設置爲多大。程序員
集合特色:
1,用於存儲對象的容器。
2,集合的長度是可變的。
3,集合中不能夠存儲基本數據類型值。
編程
java容器類庫用途是保存對象。分爲2類:設計模式
1. Collection數組
一個獨立元素的序列,這些元素都服從一條或多條規則。List必須按照插入的順序保存元素,Set不能有重複元素。Queue按照排隊規則來肯定對象產生的順序(一般與插入的順序相同)。數據結構
2. Map併發
一組成對的鍵值對對象,容許使用鍵來查找值,將數字和對象關聯到一塊兒。映射表容許咱們使用另外一個對象來查找某個對象,也被稱爲關聯數組或字典。Map很強大框架
List接口在Collection的基礎上添加了大量的方法,使得能夠在List中間插入和移除元素。ide
1 ArrayList和 LinkedList
都按照被插入的順序保存元素,區別在於執行某些操做時的性能。且LinkedList包含的操做也多於ArrayList.
(1)ArrayList :優點隨機訪問元素比較快,有連續的數組空間,可是在List的中間插入和移除元素時較慢,須要大量的移動內部的元素。
你能夠把ArrayList 當作「能夠自動擴充自身的數組」來看待,使用ArrayList也至關簡單:建立一個實例,用add()插入對象;而後用get()訪問這些對象,此時須要索引,就像數組同樣,可是不須要方括號。ArrayList還有一個size()方法,使你知道有多少個元素添加進來,從而不會不當心因索引越界而引起錯誤。
(2)LinkedList:在LinkedList中間插入刪除較快,提供優化的順序訪問。隨機訪問時較慢,特性集較ArrayList 大。各類Queue以及棧的行爲,由LinkedList提供支持。
1.HashSet TreeSet LinkedHashSet
輸出顯示在Set中,每一個相同的項只保存一次,但存儲的方式不一樣:
(1) Hashset存儲方式複雜,但保證了最快的獲取速度
(2)TreeSet按照升序保存對象
(3)LinkedHashSet按照添加的順序保存對象
可使用鍵來查找對象,相似於數組下標。Map.put(key,value)插入數據,Map.get(key)查找數據。鍵要求惟一。存儲方式不是順序存儲,速度快。沒必要指定Map的尺寸,由於它本身會自動的調整。
(1)HashMap使用最快的查找技術,存儲無順序。
(2)TreeMap按照比較結果升序保存。
(3)LinkedHashMap按照插入順序保存鍵,同時保留HashMap的查詢速度。
容器缺點:使用容器,必須對容器的確切類型進行編程,但若像更換或擴展至其餘容器,必須重寫代碼。迭代器能夠解決這個問題,實現代碼的重用。它是一個對象,它的工做是遍歷並選擇序列中的對象,而客戶端程序員沒必要知道或關心該序列底層的結構。它是輕量級對象,建立的代價小。
所以常常對迭代器有些奇怪的限制:
1)使用方法Iterator()要求容器返回一個Iterator。Iterator將準備好返回序列中的第一個元素。
2)使用next()得到序列的下一個元素。
3)使用hasNext()檢查序列中是否還有元素。
4)使用remove()將迭代器新近返回的元素刪除。
迭代器可以將遍歷序列的操做與序列底層的結構分離,它統一了對容器的訪問方式,這是它的威力所在。
框架的頂層Collection接口:
Collection的常見方法:
1,添加。
boolean add(Object obj):
boolean addAll(Collection coll):
2,刪除。
boolean remove(object obj):
boolean removeAll(Collection coll);
void clear();
3,判斷:
boolean contains(object obj):
boolean containsAll(Colllection coll);
boolean isEmpty():判斷集合中是否有元素。
4,獲取:
int size():
Iterator iterator():取出元素的方式:迭代器。
該對象必須依賴於具體容器,由於每個容器的數據結構都不一樣。
因此該迭代器對象是在容器中進行內部實現的。
對於使用容器者而言,具體的實現不重要,只要經過容器獲取到該實現的迭代器的對象便可,
也就是iterator方法。
Iterator接口就是對全部的Collection容器進行元素取出的公共接口。
5,其餘:
boolean retainAll(Collection coll);取交集。
Object[] toArray():將集合轉成數組。
package cn.itcast.p3.collection.demo; import java.util.ArrayList; import java.util.Collection; public class CollectionDemo { /** * @param args */ public static void main(String[] args) { /*Collection coll = new ArrayList(); show(coll); */ Collection c1 = new ArrayList(); Collection c2 = new ArrayList(); show(c1,c2); } public static void show(Collection c1,Collection c2){ //給c1添加元素。 c1.add("abc1"); c1.add("abc2"); c1.add("abc3"); c1.add("abc4"); //給c2添加元素。 c2.add("abc2"); c2.add("abc5"); c2.add("abc6"); System.out.println("c1:"+c1);//c1:[abc1, abc2, abc3, abc4] System.out.println("c2:"+c2);//c2:[abc2, abc5, abc6] //將c2中的元素添加到c1集合中,添加一堆 c1.addAll(c2); System.out.println(c1);//[abc1, abc2, abc3, abc4, abc2, abc5, abc6] //演示removeAll //將兩個集合中的相同元素從調用removeAll的集合中刪除,從c1中刪除c1和c2相同的元素 /* boolean b = c1.removeAll(c2); System.out.println("removeAll:"+b); System.out.println("c1"+c1);//c1[abc1, abc3, abc4] */ //演示containsAll,c1集合中是否包含C2中的全部元素,包含返回true boolean b1 = c1.containsAll(c2); System.out.println("containsAll:"+b1);
//演示retainAll 取交集,保留和指定的集合相同的元素,而刪除不一樣的元素。和removeAll功能相反 。
//c2:[abc2, abc5, abc6],
//addAll後的C1:[abc1, abc2, abc3, abc4, abc2, abc5, abc6] // boolean b = c1.retainAll(c2); // System.out.println("retainAll:"+b); // System.out.println("c1:"+c1);//c1:[abc2, abc2, abc5, abc6] } /** * 測試集合 Collection集合中的方法 * @param coll */ public static void show(Collection coll){ //1,添加元素。add. coll.add("abc1"); coll.add("abc2"); coll.add("abc3"); System.out.println(coll); //2,刪除元素。remove if(coll.contains("abc2")){ coll.remove("abc2");//會改變集合的長度 } //清空集合 //coll.clear();//清空集合中的元素,可是集合還在,集合爲[]空 System.out.println(coll.contains("abc3")); System.out.println(coll); } }
Collection集合的遍歷:使用Iterator
import java.util.ArrayList; import java.util.Collection; import java.util.Iterator; public class IteratorDemo { /** * java.util.NoSuchElementException */ public static void main(String[] args) { Collection coll = new ArrayList(); coll.add("abc1"); coll.add("abc2"); coll.add("abc3"); coll.add("abc4"); System.out.println(coll);//[abc1, abc2, abc3, abc4] //使用了Collection中的iterator()方法。 調用集合中的迭代器方法,是爲了獲取集合中的迭代器對象。 Iterator it = coll.iterator(); while(it.hasNext()){ System.out.println(it.next()); } /* for(Iterator it = coll.iterator(); it.hasNext(); ){ System.out.println(it.next()); }*/ } }
Collection
|--List:有序(存入和取出的順序一致),元素都有索引(角標),元素能夠重複。
|--Set:元素不能重複,無序。
import java.util.ArrayList; import java.util.List; /** * List:特有的常見方法:有一個共性特色就是均可以操做角標。 1,添加 void add(index,element); void add(index,collection); 2,刪除; Object remove(index): 3,修改: Object set(index,element); 4,獲取: Object get(index); int indexOf(object);獲取指定元素的索引 int lastIndexOf(object); List subList(from,to); * * */ public class ListDemo { /** * @param args */ public static void main(String[] args) { List list = new ArrayList(); show(list); } public static void show(List list) { //添加元素 list.add("abc1"); list.add("abc2"); list.add("abc3"); System.out.println(list);//[abc1, abc2, abc3] //插入元素,在列表的指定位置插入元素 list.add(1,"abc9"); System.out.println(list);//[abc1, abc9, abc2, abc3] //刪除元素。 System.out.println("remove:"+list.remove(2));//remove:abc2 //修改元素。 System.out.println("set:"+list.set(1, "abc8"));//set:abc9 //獲取元素。 System.out.println("get:"+list.get(0));//get:abc1 System.out.println(list);//[abc1, abc8, abc3] //獲取子列表。 System.out.println("sublist:"+list.subList(1, 3));//sublist:[abc8, abc3] //根據對象獲取位置 System.out.println(list.indexOf("abc8"));//1 System.out.println(list.lastIndexOf("abc3"));//2 System.out.println(list);//[abc1, abc8, abc3] } }
List的遍歷方式以及使用,使用Iterator接口的子接口ListIterator來完成在迭代中對集合元素進行的增刪改查,不會拋出併發修改的異常
import java.util.ArrayList; import java.util.Iterator; import java.util.List; import java.util.ListIterator; public class ListDemo2 { /** * @param args */ public static void main(String[] args) { List list = new ArrayList(); showListIterator(list); } /** * 可使用Iterator接口的子接口ListIterator來完成在迭代中對集合元素進行的增刪改查,不會拋出併發修改的異常 * 線程只操做迭代對象,不修改集合,這就不是併發的操做,是迭代對象ListIterator中本身的增刪改方法,而不是調用集合中的方法 * @param list */ public static void showListIterator(List list){ list.add("abc1"); list.add("abc2"); list.add("abc3"); list.add("abc4"); list.add("abc5"); System.out.println("list:"+list); ListIterator it = list.listIterator(); while(it.hasNext()){ Object obj = it.next(); if(obj.equals("abc4")){ //it.add("abc9");//不是list.add it.set("abc9"); } else System.out.print(" "+obj); } System.out.print("\n"); System.out.println("********************************"); //System.out.println("hasnext:"+it.hasNext()); //System.out.println("hasPrevious:"+it.hasPrevious()); //System.out.println("previous:"+it.previous()); //逆向遍歷 while(it.hasPrevious()){ System.out.print(" "+it.previous());//輸出 abc5 abc9 abc3 abc2 abc1 } System.out.print("\n"); System.out.println("********************************"); System.out.println(list); } /** * java.util.ConcurrentModificationException:當方法檢測到對象的併發修改,但不容許這種修改時,拋出此異常 * 集合和迭代器同時對元素進行修改,就會產生異常,一個線程對collection集合迭代,另外一個對Collection進行修改的時候, * 就會出現上面的異常 * @param list */ public static void showConcurrentModificationException(List list){ list.add("abc1"); list.add("abc2"); list.add("abc3"); System.out.println("list:"+list); Iterator it = list.iterator(); while(it.hasNext()){ Object obj = it.next();//java.util.ConcurrentModificationException //在迭代器過程當中,不要使用集合操做元素,容易出現異常。 //可使用Iterator接口的子接口ListIterator來完成在迭代中對元素進行更多的操做。 if(obj.equals("abc2")){ list.add("abc9"); } else System.out.println("next:"+obj); } System.out.println(list); } /** * List集合的遍歷,下面兩種方法均可以 * @param list */ public static void show(List list) { list.add("abc1"); list.add("abc2"); list.add("abc3"); list.add("abc4"); //第一種使用iterator Iterator it = list.iterator(); while(it.hasNext()){ System.out.println("next:"+it.next()); } //list特有的取出元素的方式之一。 for(int x=0; x<list.size(); x++){ System.out.println("get:"+list.get(x)); } } }
List:
|--Vector:內部是數組數據結構,是同步的。增刪,查詢都很慢!
|--ArrayList:內部是數組數據結構,是不一樣步的。替代了Vector。查詢的速度快。
|--LinkedList:內部是鏈表數據結構,是不一樣步的。增刪元素的速度很快。
Vector:
import java.util.Enumeration; import java.util.Iterator; import java.util.Vector; public class VectorDemo { /**Enumeration枚舉接口的功能和Iterator迭代器接口的功能是重複的,Iterator接口添加了一個可選的移除方法,並使用較短的方法名 * java1.2開始,使用Iterator替代Enumeration * @param args */ public static void main(String[] args) { Vector v = new Vector(); v.addElement("abc1"); v.addElement("abc2"); v.addElement("abc3"); v.addElement("abc4"); Enumeration en = v.elements(); while(en.hasMoreElements()){ System.out.println("nextelment:"+en.nextElement()); } Iterator it = v.iterator(); while(it.hasNext()){ System.out.println("next:"+it.next()); } } }
ArrayList
package cn.itcast.p.bean; public class Person { private String name; private int age; public Person() { super(); } public Person(String name, int age) { super(); this.name = name; this.age = age; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } public String toString(){ return name+":"+age; } }
}
import java.util.ArrayList; import java.util.Iterator; import cn.itcast.p.bean.Person; public class ArrayListTest { /** * @param args */ public static void main(String[] args) { ArrayList<Person> al = new ArrayList<Person>(); al.add(new Person("listP1",21)); al.add(new Person("listP1",22)); al.add(new Person("listP2",23)); al.add(new Person("listP3",24)); System.out.println(al);//[listP1:21, listP1:22, listP2:23, listP3:24] Iterator it = al.iterator(); while(it.hasNext()){ Person p = (Person) it.next(); System.out.println(p.getName()+"--"+p.getAge()); } } }
輸出:
[listP1:21, listP1:22, listP2:23, listP3:24]
listP1--21
listP1--22
listP2--23
listP3--24
LinkedList:
addFirst();
addLast():
jdk1.6
offerFirst();
offetLast();
getFirst();.//獲取但不移除,若是鏈表爲空,拋出NoSuchElementException.
getLast();
jdk1.6
peekFirst();//獲取但不移除,若是鏈表爲空,返回null.
peekLast():
removeFirst();//獲取並移除,若是鏈表爲空,拋出NoSuchElementException.
removeLast();
jdk1.6
pollFirst();//獲取並移除,若是鏈表爲空,返回null.
pollLast();
import java.util.Iterator; import java.util.LinkedList; public class LinkedListDemo { /** * @param args */ public static void main(String[] args) { LinkedList link = new LinkedList(); link.addFirst("abc1"); link.addFirst("abc2"); link.addFirst("abc3"); link.addFirst("abc4"); System.out.println(link); System.out.println("使用getFirst---"+link.getFirst());//獲取第一個但不刪除。當鏈表爲空的時候會拋出拋出NoSuchElementException System.out.println("使用getLast---"+link.getLast());//獲取最後一個元素,當鏈表爲空的時候會拋出拋出NoSuchElementException System.out.println("使用peekFirst---"+link.peekFirst());//獲取第一個元素,當鏈表爲爲空的時候不會報異常 System.out.println("使用peekLast---"+link.peekLast());//獲取最後一個元素 // System.out.println("使用link.removeFirst---"+link.removeFirst());//獲取第一個元素可是會刪除。abc4,當鏈表爲空的時候會拋出拋出NoSuchElementException // System.out.println("使用removeFirst---"+link.removeFirst());//abc3 // System.out.println("使用removeLast---"+link.removeLast());//獲取最後一個元素,並移除abc1 System.out.println("使用pollFirst---"+link.pollFirst());//獲取第一個元素並從集合中移除(1.6,出來的新方法,當鏈表爲爲空的時候不會報異常) System.out.println("使用pollFirst---"+link.pollFirst()); System.out.println("使用pollLast---"+link.pollLast());//獲取最後一個元素並從集合中移除 System.out.println("使用pollLast---"+link.pollLast()); // while(!link.isEmpty()){ // System.out.println(link.removeLast()); // } System.out.println(link); // Iterator it = link.iterator(); // while(it.hasNext()){ // System.out.println(it.next()); // } } }
Set:元素不能夠重複,是無序。
Set接口中的方法和Collection一致。
|--HashSet: 內部數據結構是哈希表 ,是不一樣步的。
如何保證該集合的元素惟一性呢?
是經過對象的hashCode和equals方法來完成對象惟一性的。
若是對象的hashCode值不一樣,那麼不用判斷equals方法,就直接存儲到哈希表中。
若是對象的hashCode值相同,那麼要再次判斷對象的equals方法是否爲true。
若是爲true,視爲相同元素,不存。若是爲false,那麼視爲不一樣元素,就進行存儲。
記住:若是元素要存儲到HashSet集合中,必須覆蓋hashCode方法和equals方法。
通常狀況下,若是定義的類會產生不少對象,好比人,學生,書,一般都須要覆蓋equals,hashCode方法。
創建對象判斷是否相同的依據。
若是HashSet不覆蓋equal和hashCode方法的話,默認的是使用Object中的equal和hashCode方法
Object中的equal方法比較地址的,而不是比較內容,若是添加劇復的對象,地址不一樣,就會認爲沒有重複的對象
因此比較對象是否相同,必須覆蓋equal和hashCode方法
package cn.itcast.p.bean; public class Person /*extends Object*/ { private String name; private int age; public Person() { super(); } public Person(String name, int age) { super(); this.name = name; this.age = age; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } public String toString(){ return name+":"+age; } @Override public boolean equals(Object obj) {//判斷人的內容是否相同 System.out.println("調用了equals方法---------------"); if(this == obj) //this只是否爲Person對象 return true; if(!(obj instanceof Person)){ throw new ClassCastException("類型轉化錯誤!"); } Person p = (Person)obj; return this.name.equals(p.name) && this.age == p.age;//字符創name的內容相同嗎 } @Override public int hashCode() { //判斷人的hash值是否相同 System.out.println("調用了hashCode方法---------------"); return name.hashCode()+ age; } }
往hashSet裏面添加元素,進行遍歷:
package cn.itcast.p4.hashset.test; import java.util.HashSet; import java.util.Iterator; import cn.itcast.p.bean.Person; /* * 往hashSet集合中存儲Person對象。若是姓名和年齡相同,視爲同一我的。視爲相同元素。 */ public class HashSetTest { /** * @param args */ public static void main(String[] args) { HashSet hs = new HashSet(); /* * HashSet集合數據結構是哈希表,因此存儲元素的時候,咱們須要覆蓋hashCode方法和equal方法,來確保放入的對象的惟一性 * 使用的元素的hashCode方法來肯定位置,若是位置相同, * 在經過元素的equals來肯定是否相同,若是相同的話,就不往set裏面存 */ hs.add(new Person("lisi4",24)); hs.add(new Person("lisi7",27)); hs.add(new Person("lisi1",21)); hs.add(new Person("lisi9",29)); hs.add(new Person("lisi7",27)); Iterator it = hs.iterator(); while(it.hasNext()){ Person p = (Person)it.next(); //System.out.println(p); System.out.println(p.getName()+"...."+p.getAge()); } } }
輸出:
調用了hashCode方法---------------
調用了hashCode方法---------------
調用了hashCode方法---------------
調用了hashCode方法---------------
調用了hashCode方法---------------
調用了equals方法---------------
lisic....21
lisia....24
lisid....29
lisib....27
結果說明調用了5次hashCode,調用了一次equals方法,說明當執行到這句話的時候,hs.add(new Person("lisi7",27));調用了equal方法,由於hash表裏面已經有了一個name爲lisi7,年齡爲27的對象,hash值相同,須要判斷內容是否相同,調用equal方法判斷內容是否相同,相同,不往hashset裏面存儲。
TreeSet
天然排序,若是存放的是自定義對象,使用TreeSet,必須實現Comparable接口,覆蓋裏面的compareTo方法,添加元素的時候進行比較;若是添加的是字符串
就不須要覆蓋compareTo方法,由於字符串有本身的compareTo方法;
自定義對象在TreeSet存儲時候,若是不覆蓋,就會報 java.lang.ClassCastException: cn.itcast.p.bean.Person cannot be cast to java.lang.Comparable異常
public class Person /*extends Object*/ implements Comparable{ private String name; private int age; public Person() { super(); } public Person(String name, int age) { super(); this.name = name; this.age = age; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } public String toString(){ return name+":"+age; } @Override public boolean equals(Object obj) {//判斷人的內容是否相同 System.out.println("調用了equals方法---------------"); if(this == obj) //this只是否爲Person對象 return true; if(!(obj instanceof Person)){ throw new ClassCastException("類型轉化錯誤!"); } Person p = (Person)obj; return this.name.equals(p.name) && this.age == p.age;//字符創name的內容相同嗎 } @Override public int hashCode() { //判斷人的hash值是否相同 System.out.println("調用了hashCode方法---------------"); return name.hashCode()+ age; } @Override public int compareTo(Object o) { if(!(o instanceof Person)) throw new ClassCastException("類型轉化錯誤"); Person p = (Person)o; int temp = this.age-p.age; return temp==0 ? (this.name.compareTo(p.name)) : temp;//temp等於0表示年齡相等。 } }
import java.util.Iterator; import java.util.TreeSet; import cn.itcast.p.bean.Person; public class TreeSetDemo { /** * @param args */ public static void main(String[] args) { demo2(); } /* * 自定義對象,使用TreeSet,進行天然排序的時候, * 須要實現Comparable接口,添加元素的時候進行比較, * 以Person對象年齡進行排序,若是年齡相同,就按照姓名排序 * */ public static void demo2(){ TreeSet ts = new TreeSet(); ts.add(new Person("zhangsan",28)); ts.add(new Person("lisi",21)); ts.add(new Person("zhouqi",29)); ts.add(new Person("zhaoliu",25)); ts.add(new Person("wangu",24)); ts.add(new Person("zhouqi",29)); Iterator it = ts.iterator(); while(it.hasNext()){ Person p = (Person)it.next(); System.out.println(p.getName()+":"+p.getAge()); } } /** * 添加的是字符串對象,由於字符串內部實現了compareTo方法, * 因此不須要實現Comparable接口裏面的 */ public static void demo1() { TreeSet ts = new TreeSet(); ts.add("abc"); ts.add("zaa"); ts.add("aa"); ts.add("nba"); ts.add("cba"); Iterator it = ts.iterator(); while(it.hasNext()){ System.out.println(it.next()); } } }
輸出結果:先以年齡進行排序,再以姓名進行排序。
lisi:21
wangu:24
zhaoliu:25
zhangsan:28
zhouqi:29
還可使用 構造一個新的空 TreeSet,它根據指定比較器進行排序。實現比較器接口進行比較。
代碼:
TreeSet(Comparator<? super E> comparator)Comparator
public class Person{ private String name; private int age; public Person() { super(); } public Person(String name, int age) { super(); this.name = name; this.age = age; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } public String toString(){ return name+":"+age; } }
Comparator比較器:
import java.util.Comparator; import cn.itcast.p.bean.Person; /** * 建立了一個根據Person類的name進行排序的比較器。 * 先按照姓名進行比較,若是姓名相同,再按照年齡進行比較 */ public class ComparatorByName implements Comparator { @Override public int compare(Object o1, Object o2) { Person p1 = (Person)o1; Person p2 = (Person)o2; int temp = p1.getName().compareTo(p2.getName()); //比較姓名相同,在比較年齡 return temp==0?p1.getAge()-p2.getAge(): temp; // return 1;//有序。 } }
package cn.itcast.p5.treeset.demo; import java.util.Iterator; import java.util.TreeSet; import cn.itcast.p.bean.Person; import cn.itcast.p5.comparator.ComparatorByName; public class TreeSetComparator { /** * @param args */ public static void main(String[] args) { TreeSet ts = new TreeSet(new ComparatorByName()); /* * 自定義對象,使用TreeSet,進行天然排序的時候, * 須要實現Comparable接口,添加元素的時候進行比較 * * 以Person對象年齡進行排序,若是年齡相同,就按照姓名排序 * */ ts.add(new Person("zhangsan",28)); ts.add(new Person("lisi",21)); ts.add(new Person("zhouqi",29)); ts.add(new Person("zhaoliu",25)); ts.add(new Person("wangu",24)); Iterator it = ts.iterator(); while(it.hasNext()){ Person p = (Person)it.next(); System.out.println(p.getName()+":"+p.getAge()); } } }
輸出:
lisi:21
wangu:24
zhangsan:28
zhaoliu:25
zhouqi:29
package cn.itcast.p5.treeset.test; import java.util.Comparator; import java.util.Iterator; import java.util.TreeSet; import cn.itcast.p.bean.Person; import cn.itcast.p5.comparator.ComparatorByLength; /* * 對字符串進行長度排序,比較內容 * * "20 18 -1 89 2 67" */ public class TreeSetTest { /** * @param args */ public static void main(String[] args) { //接口內部類 TreeSet ts = new TreeSet(new Comparator<String>() { @Override public int compare(String o1, String o2) { int temp = o1.length()-o2.length(); return temp==0 ? o1.compareTo(o2):temp; } }); ts.add("aaaaa"); ts.add("zz"); ts.add("nbaq"); ts.add("cba"); ts.add("abc"); ts.add("abc"); Iterator it = ts.iterator(); while(it.hasNext()){ System.out.println(it.next()); } } }
輸出:
zz
abc
cba
nbaq
aaaaa
Map
import java.util.Collection; import java.util.HashMap; import java.util.Iterator; import java.util.Map; import java.util.Set; public class MapDemo { public static void main(String[] args) { Map<Integer,String> map = new HashMap<Integer,String>(); method(map); } /** * * Set<Map.Entry<K,V>> entrySet()方法:返回一個set集合,裏面裝的是Map.Entry接口類型的鍵值對象 * * 第二種遍歷map的方式:經過看API:Set<Map.Entry<K,V>> entrySet():Map.Entry<K,V>接口類型, * 裏面有K getKey() 返回與此項對應的鍵。 V getValue() 返回與此項對應的值。 * 思路:經過把map轉化爲set,進行迭代 * 經過使用entrySet方法吧鍵和值的映射關係做爲對象,存儲到set集合中,這個映射關係的類型爲Map.Entry類型 * * */ public static void method_3(Map<Integer,String> map){ map.put(8,"lisi"); map.put(2,"zhaoliu"); map.put(7,"wangwu"); map.put(6,"wangwang"); Set<Map.Entry<Integer, String>>entrySet = map.entrySet(); System.out.println(entrySet);//[2=zhaoliu, 6=wangwang, 7=wangwu, 8=lisi] Iterator<Map.Entry<Integer, String>>it = entrySet.iterator(); //System.out.println(it.next()); while(it.hasNext()){ Map.Entry<Integer, String> entryMap = it.next(); Integer key = entryMap.getKey();//獲取鍵 String value = entryMap.getValue();//獲取值 System.out.println(key+":"+value); } } /* * 第一種遍歷的方法 * Set<K> keySet():返回鍵的set集合 * 取出map中的全部元素。 * 原理,經過keySet方法獲取map中全部的鍵所在的Set集合,在經過Set的迭代器獲取到每個鍵, 在對每個鍵經過map集合的get方法獲取其對應的值便可。 */ public static void method_2(Map<Integer,String> map){ map.put(8,"zhaoliu"); map.put(2,"zhaoliu"); map.put(7,"xiaoqiang"); map.put(6,"wangcai"); Set<Integer> keySet = map.keySet(); System.out.println(keySet);//鍵的set集合[2, 6, 7, 8] Iterator<Integer> it = keySet.iterator();//迭代keySet while(it.hasNext()){ Integer key = it.next(); String value = map.get(key); System.out.println(key+":"+value); } } /** * 經常使用方法: 1,添加。 value put(key,value):返回前一個和key關聯的值,若是沒有返回null. 2,刪除。 void clear():清空map集合。 value remove(key):根據指定的key翻出這個鍵值對。 3,判斷。 boolean containsKey(key): boolean containsValue(value): boolean isEmpty(); 4,獲取。 value get(key):經過鍵獲取值,若是沒有該鍵返回null。 固然能夠經過返回null,來判斷是否包含指定鍵。 int size(): 獲取鍵值對的個數。 5.特殊方法: Collection<V> values() 包含的值的 Collection 視圖。 * @param map */ public static void method(Map<Integer,String> map){//學號和姓名 // 添加元素。 System.out.println(map.put(8, null));//null System.out.println(map.put(8, "xiaoqiang"));//wangcai 存相同鍵,值會覆蓋。 map.put(2,"zhangsan"); map.put(7,"zhaoliu"); /*System.out.println(map); //刪除。 System.out.println("remove:"+map.remove(2)); //判斷。 System.out.println("containskey:"+map.containsKey(6)); System.out.println("containsValue:"+map.containsValue("zhaoliu")); //獲取。 System.out.println("get:"+map.get(7)); System.out.println(map);*/ //返回key對應的全部value的集合 Collection<String>values = map.values(); System.out.println(values); Iterator<String>it = values.iterator(); while(it.hasNext()){ String value = it.next(); System.out.println(value); } } } interface MyMap{ public static interface MyEntry{//內部接口 void get(); } } class MyDemo implements MyMap.MyEntry{ public void get(){} } class Outer{ static class Inner{ static void show(){} } }
HashMap
public class Person { private String name; private int age; public Person() { super(); } public Person(String name, int age) { super(); this.name = name; this.age = age; } @Override public int hashCode() { final int prime = 31; int result = 1; result = prime * result + age; result = prime * result + ((name == null) ? 0 : name.hashCode()); return result; } @Override public boolean equals(Object obj) { if (this == obj) return true; if (obj == null) return false; if (getClass() != obj.getClass()) return false; Person other = (Person) obj; if (age != other.age) return false; if (name == null) { if (other.name != null) return false; } else if (!name.equals(other.name)) return false; return true; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } @Override public String toString() { return "Person:"+getName()+":"+getAge(); } }
package cn.itcast.p2.bean; public class Student extends Person { public Student() { super(); } public Student(String name, int age) { super(name, age); } @Override public String toString() { return "Student:"+getName()+":"+getAge(); } }
package cn.itcast.p7.hashmap.demo; import java.util.HashMap; import java.util.Iterator; import java.util.Set; import cn.itcast.p2.bean.Student; public class HashMapDemo { /** * @param args */ public static void main(String[] args) { /* * 將學生對象和學生的歸屬地經過鍵與值存儲到map集合中。 * */ HashMap<Student,String> hm = new HashMap<Student,String>(); hm.put(new Student("lisi",38),"北京"); hm.put(new Student("zhaoliu",24),"上海"); hm.put(new Student("xiaoqiang",31),"瀋陽"); hm.put(new Student("wangcai",28),"大連"); hm.put(new Student("zhaoliu",24),"鐵嶺"); // Set<Student> keySet = hm.keySet(); // Iterator<Student> it = keySet.iterator(); Iterator<Student> it = hm.keySet().iterator(); while(it.hasNext()){ Student key = it.next(); String value = hm.get(key); System.out.println(key.getName()+":"+key.getAge()+"---"+value); } } }
結果:
xiaoqiang:31---瀋陽
wangcai:28---大連
lisi:38---北京
zhaoliu:24---鐵嶺
HashMap要比較自定義對象也必須重寫equal方法和hashCode方法。
TreeMap
排序,實現Comparator接口
package cn.itcast.p3.comparator; import java.util.Comparator; import cn.itcast.p2.bean.Person; public class ComparatorByName implements Comparator<Person> { @Override public int compare(Person o1, Person o2) { int temp = o1.getName().compareTo(o2.getName()); return temp==0? o1.getAge()-o2.getAge(): temp; } }
package cn.itcast.p8.treemap.demo; import java.util.Iterator; import java.util.Map; import java.util.TreeMap; import cn.itcast.p2.bean.Student; import cn.itcast.p3.comparator.ComparatorByName; public class TreeMapDemo { /** * @param args */ public static void main(String[] args) { TreeMap<Student,String> tm = new TreeMap<Student,String>(new ComparatorByName()); tm.put(new Student("lisi",38),"北京"); tm.put(new Student("zhaoliu",24),"上海"); tm.put(new Student("xiaoqiang",31),"瀋陽"); tm.put(new Student("wangcai",28),"大連"); tm.put(new Student("zhaoliu",24),"鐵嶺"); Iterator<Map.Entry<Student, String>> it = tm.entrySet().iterator(); while(it.hasNext()){ Map.Entry<Student,String> me = it.next(); Student key = me.getKey(); String value = me.getValue(); System.out.println(key.getName()+":"+key.getAge()+"---"+value); } } }
輸出結果:
lisi:38---北京
wangcai:28---大連
xiaoqiang:31---瀋陽
zhaoliu:24---鐵嶺
LinkedHashMap
package cn.itcast.p1.map.demo; import java.io.File; import java.util.HashMap; import java.util.Iterator; import java.util.LinkedHashMap; import java.util.Map; public class LinkedHashMapDemo { /** * LinkedHashMap 按順序存入,按順序取出 */ public static void main(String[] args) { File f= null; HashMap<Integer,String> hm = new LinkedHashMap<Integer,String>(); hm.put(7, "zhouqi"); hm.put(3, "zhangsan"); hm.put(1, "qianyi"); hm.put(5, "wangwu"); Iterator<Map.Entry<Integer,String>> it = hm.entrySet().iterator(); while(it.hasNext()){ Map.Entry<Integer,String> me = it.next(); Integer key = me.getKey(); String value = me.getValue(); System.out.println(key+":"+value); } } }