Java-17 集合、正則、map簡單介紹
1.SimpleDateFormat
-
SimpleDateFormat主要用於將日期進行格式化,可以將Date轉成指定格式的字串,也可以將字串轉成日期。
-
構造方法:
public SimpleDateFormat() 預設格式做轉換 public SimpleDateFormat(String pattern) 按指定格式做轉換
-
成員方法:
public String format(Date date); public Date parse(Strig dateStr) throws ParseExcepiton;
-
format方法 date->string
import java.text.SimpleDateFormat; import java.util.Date; public class SimpleDateFormatDemo1 { public static void main(String[] args) { // 獲取當前時間 Date date = new Date(); System.out.println(date); // 無參構造方法。預設格式 xxxx/xx/xx 上午 xx:xx SimpleDateFormat sdf = new SimpleDateFormat(); String str = sdf.format(date); System.out.println(str);// 2020/10/17 上午10:32 SimpleDateFormat sdf2 = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); String str2 = sdf2.format(date); System.out.println(str2);// 2020-10-17 10:35:46 } }
-
parse方法 string-->date
public class SimpleDateFormatDemo1 { // throws ParseException丟擲異常 public static void main(String[] args) throws ParseException { // 宣告Str date格式 SimpleDateFormat sdf3 = new SimpleDateFormat("yyyy-MM-dd HH/mm/ss"); String str3 = "2010-02-02 12/12/12"; // Str 轉 date Date date2 = sdf3.parse(str3); System.out.println(date2); } }
注意:一定要保證String的格式 和 SimpleDateFormat中的Patten 保持一致。
-
日期轉換練習
// 把字串"2018-10-15 11:11:11" 轉成字串 "11:11:11 15/10/2018" import java.text.ParseException; import java.text.SimpleDateFormat; import java.util.Date; public class SimpleDateFormatDemo2 { public static void main(String[] args) throws ParseException { String str1 = "2018-10-15 11:11:11"; SimpleDateFormat sdf1 = new SimpleDateFormat("yyyy-MM-dd HH:mm:SS"); // 轉換成date Date date = sdf1.parse(str1); System.out.println(date);// Mon Oct 15 11:11:00 CST 2018 SimpleDateFormat sdf2 = new SimpleDateFormat("SS:mm:HH dd/MM/yyyy"); String str2 = sdf2.format(date); // 轉化成String System.out.println(str2);// 11:11:11 15/10/2018 } }
2.正則表示式
-
正則表示式是對字串操作的一種邏輯公式,就是用事先定義好的一些特定字元,及這些特定字元的組合,組成一個"規則字串"。這個“規則字串”的一種過濾。
-
練習
// 驗證qq號,不能以0開頭 ,5-15位 public class RegexDemo1 { public static void main(String[] args) { Scanner sc = new Scanner(System.in); System.out.println("請輸入QQ號:"); String qq = sc.next(); boolean result = checkQQ(qq); if (result) { System.out.println("合法QQ"); } else { System.out.println("不合格QQ"); } } private static boolean checkQQ(String qq) { String regex = "[1-9][0-9]{4,14}"; return qq.matches(regex); } }
-
常用規則:
. 任何字元 \d 數字[0-9] \D 非數字 [^0-9] \s 空白字元 \r\n\x0B\f\r \S 非空白字元 \w 單詞字元 [a-zA-Z_0-9] \W 非單詞字元 X? X的0次或1次 X* X的0次或多次 x+ X的一次或多次 X{n} X的n次 X{n,} X的至少n次 X{n,m} 至少n次,不超過m次 [abc]a、b 或 c (簡單類) \b 單詞邊界
-
匹配一個整數或小數
System.out.println("12.34".matches("\\d+(\\.\\d+)?"));
-
匹配手機號
String phoneRegex = "^((13[0-9])|(14[5|7])|(15([0-3]|[5-9]))|(17[013678])|(18[0,5-9]))\\d{8}$"; System.out.println("13500000000".matches(phoneRegex));
-
驗證郵箱
String emailRegex = "^([a-z0-9A-Z]+[-|_|\\.]?)+[a-z0-9A-Z]@([a-z0-9A-Z]+(-[a-z0-9A-Z]+)?\\.)+[a-zA-Z]{2,}$"; System.out.println("[email protected]".matches(emailRegex));
-
split分割
public class RegxDemo2 { public static void main(String[] args) { String str1 = "11,22,33"; String[] split1 = str1.split(","); System.out.println(split1[1]); String str2 = "11.22.33"; String[] split2 = str2.split("\\."); System.out.println(split2[1]); String path = "C:\\demo\\a.txt"; String[] split3 = path.split("\\\\"); System.out.println(split3[2]); } }
-
練習:有一個字串 "2 3 1 11 4" 轉成"1 2 3 4 11"
public class RegexDemo3 { public static void main(String[] args) { String str = "2 3 1 11 4"; String[] arr = str.split(" "); // 建立等長int陣列 int[] arr2 = new int[arr.length]; for (int i=0;i<arr.length;i++) { String s = arr[i]; int a = Integer.parseInt(s); arr2[i] = a;// 把轉成int值儲存int陣列 } // 對int陣列排序 Arrays.sort(arr2); // 遍歷拼接 StringBuilder builder = new StringBuilder(); for (int i=0;i<arr2.length;i++) { builder.append(arr2[i]).append(" "); } System.out.println(builder.toString().trim()); } }
-
練習:
// 1+2+3+4...+10=55 public class LianxiaddDemo { public static void main(String[] args) { StringBuilder s = new StringBuilder(); int sum = 0; // for迴圈不能使用 加號 拼接字串否則效能很低。 for (int i=1;i<=10;i++) { s.append(i).append("+"); sum += i; } String s2 = s.substring(0, s.length()-1); System.out.println(s2 + "=" + sum); } }
-
正則替換
replaceAll();
-
把手機號中間四位替換*
public class RegexDemo4 { public static void main(String[] args) { String mobile = "13333333333"; String result = mobile.replaceAll("(\\d{3})(\\d{4})(\\d{4})", "$1****$3"); System.out.println(result); } }
-
獲取三個字母單詞
import java.util.regex.Pattern; import java.util.regex.Matcher; public class RegexDemo5 { public static void main(String[] args) { String str = "ni hao a wo jiao xiao liu ? ni shi shui?"; // 獲取Pattern物件 Pattern p = Pattern.compile("\\b[a-zA-Z]{3}\\b"); // 獲取Matcher, Matcher 中封裝了所有匹配結果 Matcher m = p.matcher(str); // 獲取結果 while (m.find()) { System.out.println(m.group()); // hao // liu // shi } } }
注意:m.group不能單獨使用,需要先m.find才能使用m.group
3.集合
-
面嚮物件語言對事務的體現都是以物件形式,所以為了方便對多個物件的操作,Java提供了集合類。
-
陣列和集合類同是容器,它們不同?
1.陣列雖然也可以儲存物件,但長度是固定的,集合長度是可變的。 2.陣列中可以儲存基本資料型別,集合只能儲存物件。
-
集合缺點:
集合只能用於儲存物件,集合長度是可變的,集合可以儲存不同型別物件。
-
集合類關係圖:
虛線表示介面,實線表示類
-
Collection中方法
-
add 新增
Collection c = new ArrayList(); c.add(123);// 123是Integer型別 c.add(12.4); c.add("helloworld"); System.out.println(c);// [123, 12.4, helloworld]
-
remove 移除
boolean r = c.remove(123); System.out.println(r );// true
-
clear清空
-
isEmpty是否為空
System.out.println(c.isEmpty());
-
size集合長度
System.out.println(c.size());
-
contains包含
System.out.println(c.contains(12.4));
-
addAll 新增所有
import java.util.ArrayList; import java.util.Collection; import java.util.LinkedList; public class CollectionDemo2 { public static void main(String[] args) { Collection c1 = new ArrayList(); c1.add("c1-1"); c1.add("c1-2"); c1.add("c1-3"); Collection c2 = new LinkedList(); c2.add("c2-1"); c2.add("c2-2"); c2.add("c2-3"); // c2 元素 新增 c1中 c1.addAll(c2); System.out.println(c1); } }
-
removeAll 移除所有
c1.removeAll(c2);
-
containsAll 是否全部包含
c1.containsAll(c2);
-
retainAll 取交集
c1.retainAll(c2)
-
-
Collection 遍歷
- 一種集合轉陣列,另一種通過迭代器遍歷。
import java.util.ArrayList; import java.util.Collection; import java.util.Iterator; public class CollectionDemo3 { public static void main(String[] args) { Collection c = new ArrayList(); c.add("1"); c.add("1"); c.add("2"); c.add("3"); c.add("4"); System.out.println(c); // 1.集合轉資料 Object[] array = c.toArray(); // 遍歷 for (int i=0;i<array.length;i++) { System.out.println(array[i]); } // 2.迭代器 Iterator it = c.iterator(); // 判斷是否有下一個值 while (it.hasNext()) { // 列印下一個值 System.out.println(it.next()); } } }
-
List中方法
-
有序的,元素可以重複
-
add(int index,E element) 插入
import java.util.ArrayList; import java.util.Collection; import java.util.List; public class ListDemo1 { public static void main(String[] args) { // 泛型:限制集合中的元素只能儲存某一種的資料型別(jdk>=1.5) /** * 泛型只在編譯時有效,再底層.class檔案中沒有泛型(泛型的擦除)。 * */ Collection c = new ArrayList(); List<String> list = new ArrayList<> (); list.add("哈");// Collection 中方法 list.add(0, "呼");// ArrayList 中的方法 System.out.println(list);// [呼, 哈] } }
- remove(int index) 根據索引值移除元素
list.remove(1);
- get(int index) 根據索引值取元素
list.get(1); // 可以通過for迴圈遍歷 for (int i=0;i<list.size();i++){ System.out.println(list.get(i)); }
- set(int index)
list.set(1, "呵");
- ListIterator listIterator
List<String> list = new ArrayList<> (); // hashPrevious 檢視前面是否有元素 while (it.hashPrevious){ System.out.println(it.previous()); } // 上面相當於從後往前遍歷。 // 需要注意是,要想從後往前遍歷,需要先從前往後遍歷以邊,將指標指到最後位置,先執行如下類似邏輯程式碼。 while (it.hasNext()){ System.out.println(it.next()); }
-
-
四種遍歷方式
import java.util.List; import java.util.ArrayList; import java.util.Iterator; import java.util.ListIterator; public class ListTestDemo { public static void main(String[] args) { List<Person> list = new ArrayList<> (); Person p1 = new Person("Tom", '男', 23); Person p2 = new Person("Lucy", '女', 20); list.add(p1); list.add(p2); // 1.轉陣列方式 Object[] arr1 = list.toArray(); for (int i=0;i<arr1.length;i++) { System.out.println(arr1[i]); } System.out.println("------------------"); // 2.迭代器方式 Iterator arr2 = list.iterator(); while (arr2.hasNext()) { System.out.println(arr2.next()); } System.out.println("------------------"); // 3.for get方式 for (int i=0;i<list.size();i++) { System.out.println(list.get(i)); } System.out.println("------------------"); // 4.ListIterator ListIterator<Person> it2 = list.listIterator(); while (it2.hasNext()) { System.out.println(it2.next()); } } } class Person{ String name; char gender; int age; public Person() { } public Person(String name,char gender,int age) { super(); this.name = name; this.age = age; this.gender = gender; } @Override public String toString() { return "Person [name=" + name + ", gender=" + gender + ", age=" + age + "]"; } }
-
練習:將"張三,18,男;李四,20,男;王五,33,男"切分建立Person物件,並存儲在集合中。
List<Person> list2 = new ArrayList<> (); String str2 = "張三,18,男;李四,20,男;王五,33,男"; String[] a1 = str2.split(";"); for (int i=0; i<a1.length ;i++) { String sa = a1[i]; String[] a2 = sa.split(","); String name = a2[0]; int age = Integer.parseInt(a2[1]); char gender = a2[2].charAt(0); Person p = new Person(name,gender,age); list2.add(p); } System.out.println(list2); }
-
List中去重:
- 方式1:新建一個空集合,新增元素前判斷當前序列有沒有該元素,沒有就新增,有就放棄新增。
- 方式2:在原有集合上,前一個元素和後一個元素進行對比,重複進行刪除操作。刪除會造成序列元素變少,索引值應回到原來索引位置。
import java.util.ArrayList; import java.util.List; public class ListquchongDemo { public static void main(String[] args) { List<String> list = new ArrayList<>(); list.add("大哥"); list.add("二哥"); list.add("大哥"); list.add("三哥"); list.add("大哥"); List<String> r = distinct(list); System.out.println(r );// [大哥, 二哥, 三哥] List<String> r2 = distinct2(list); System.out.println(r2); } public static List<String> distinct2(List<String> list) { for (int i=0;i<list.size()-1;i++) { for (int j=i+1; j<list.size();j++) { if (list.get(i).equals(list.get(j))) { list.remove(j); j--; } } } return list; } public static List<String> distinct(List<String> list){ // 建立一個新的集合,用於存放不重複的元素 List <String> result =new ArrayList<>(); // 從要去重的集合中拿到每一個元素,去新的集合中做判斷,如果新的集合中不存在, // 則存入新的集合,如果新的集合存在,就不存。 for (int i=0;i<list.size();i++) { String s = list.get(i); if (!result.contains(s)) { result.add(s); } } // 返回結果 return result; } }
-
Object型別List去重
import java.util.List; import java.util.ArrayList; public class ListTest2 { // 屬性值去重方式,通過重寫hashCode和equals public static void main(String[] args) { List <Personss> list = new ArrayList<> (); list.add(new Personss("張三", 12,'男')); list.add(new Personss("李四", 15,'男')); list.add(new Personss("王二", 19,'男')); list.add(new Personss("張三", 12,'男')); List<Personss> r = distinct(list); System.out.println(list); } public static List<Personss> distinct(List<Personss> list){ List <Personss> result = new ArrayList(); for (int i=0;i<list.size();i++) { Personss p = list.get(i); if (!result.contains(p)) { result.add(p); } } return result; } } class Personss{ String name; int age; char gender; public Personss() {} public Personss(String name, int age,char gender) { this.age = age; this.name = name; this.gender = gender; } @Override public int hashCode() { final int prime = 31; int result = 1; result = prime * result + age; result = prime * result + gender; 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; Personss other = (Personss) obj; if (age != other.age) return false; if (gender != other.gender) return false; if (name == null) { if (other.name != null) return false; } else if (!name.equals(other.name)) return false; return true; } @Override public String toString() { return "Person [name=" + name + ", age=" + age + ", gender=" + gender + "]"; } }
-
LinkList
-
陣列中,增刪慢,當擴容需要移動元素,消耗大量空間,它內部元素是連續的,並且有索引值,查詢塊。而ArrayList底層是陣列實現的。所以它特點是增刪慢,查詢快。
-
而連結串列內元素地址不是連續的,內部每個元素為一個節點,每個節點指向下一個元素(儲存下一個元素地址值)。它的特點增刪快,查詢慢。而LinkList底層是連結串列實現的(隨機查詢慢)。
-
LinkList獨有方法
import java.util.List; import java.util.LinkedList; public class LinkListDemo { public static void main(String[] args) { LinkedList <Integer> list = new LinkedList<> (); list.add(10); list.add(20); list.add(30); // 頭部新增元素 list.addFirst(100); // 尾部新增元素 list.addLast(200); System.out.println(list);// [100, 10, 20, 30, 200] // 獲取頭部元素 System.out.println(list.getFirst());// 100 // 獲取尾部元素 System.out.println(list.getLast());// 200 // 移除尾部元素 list.removeLast(); // 移除頭部元素 list.removeFirst(); System.out.println(list);// [10, 20, 30] } }
-
4.for each迴圈
-
for迴圈,從jdk5產生的新特性,主要用於集合或陣列遍歷。
-
格式:
for (資料型別 變數名:陣列名/集合名){ // 變數名: 集合中的每一個元素 }
-
示例:
import java.util.List; import java.util.ArrayList; import java.util.Collection; public class ForeachDemo { public static void main(String[] args) { // 陣列迴圈 int[] arr = new int[] {5,12,53,0,11}; for (int a:arr) { System.out.println(a); } // List for迴圈 List<Integer> list = new ArrayList<> (); list.add(100); list.add(200); list.add(300); for (Integer i:list) { System.out.println(i); } // Collection Collection c = new ArrayList(); c.add(123); c.add(456); c.add(789); for (Object o:c) { System.out.println(o); } } }
5.可變引數
-
用於定義方法的時候不知道定義多少個引數。(jdk5後產生新特性)。
-
格式:
修飾符 返回值型別 方法名(資料型別... 變數名){}
-
注意:
這裡變數起始是一個數組。 如果一個方法有可變引數,並由多個引數,那麼,可變引數必須是最後一個,一個方法中最多隻能有一個可變引數。
-
示例:
public class ChangeableParamDemo { public static void main(String[] args) { System.out.println(getSum(1,2,3,4,5,6,7)); } public static int getSum(int ...a) { int sum = 0; for (int i : a) { sum += i; } return sum; } }
6.集合和陣列相互轉換
-
集合轉陣列:
import java.util.List; import java.util.ArrayList; import java.util.Arrays; public class ArrayCollectionDemo { public static void main(String[] args) { // 集合轉陣列。toArray方法 List <String> list = new ArrayList<>(); list.add("a"); list.add("b"); list.add("c"); Object[] arr = list.toArray(); // 陣列轉集合 /* * Arrays工具類中asList方法 * public static <T> List<T> asList(T... a) * T代表型別 * */ // 方式1: List<Integer> list2 = Arrays.asList(1,2,3,4,5,6); System.out.println(list2);// [1, 2, 3, 4, 5, 6] // 方式2: Integer[] arr2 = new Integer[] {3,4,6,11,2,8}; List<Integer> list3 = Arrays.asList(arr2);// 得到是Arrays中內部類,該類沒有實現add/remove System.out.println(list3);// [3, 4, 6, 11, 2, 8] // 而使用Arrays.asList 得到集合是一個只讀集合,不能進行add/remove 操作 // 通過建立一個新的ArrayList,把元素新增到新的ArrayList就可以進行add/remove操作 List<Integer> list4 = new ArrayList<>(list3); list4.add(300); System.out.println(list4); } }
7.Set用法
-
Set中元素是不能重複的,並且是無序的(沒有索引).
Set HashSet:不能保證存入和取出順序 LinkedHashSet: 能夠保證存入和取出的順序(連結串列) TreeSet:能夠對內部元素,進行排序
-
HashSet:
public class SetDemo { public static void main(String[] args) { Set<String> set = new HashSet<>(); set.add("曹操"); set.add("劉備"); set.add("張飛"); set.add("趙雲"); set.add("關羽"); set.add("劉備"); System.out.println(set);// [關羽, 張飛, 劉備, 曹操, 趙雲] } } // 可以看到上面Set元素是無序的
-
LinkHashSet
Set<String> set = new LinkedHashSet<>(); System.out.println(set);// [曹操, 劉備, 張飛, 趙雲, 關羽] // 而LinkHashSet是有序的。
-
元素不可重複性判斷是通過hashCode/equals這兩個方法決定的,它是先求出要存的元素的hashCode,看集合是否有元素的hashCode和它相同,如果沒有相同,則直接存入set裡面。如果hashCode相同,再比較equals如果true確實相同,不能存入。false可以存入。
-
set遍歷方式:
import java.util.HashSet; import java.util.Iterator; import java.util.Set; import java.util.LinkedHashSet; public class SetDemo { public static void main(String[] args) { Set<String> set = new HashSet<>(); set.add("曹操"); set.add("劉備"); set.add("張飛"); set.add("趙雲"); set.add("關羽"); set.add("劉備"); System.out.println(set);// [曹操, 劉備, 張飛, 趙雲, 關羽] // 1.toArray Object[] array = set.toArray(); for (Object o: array) { System.out.println(o); } //2.迭代器 Iterator<String> it = set.iterator(); while (it.hasNext()) { System.out.println(it.next()); } //3.foreach for(String s:set) { System.out.println(s); } } }
-
練習建立一個Set
儲存三個元素。列印集合,要求列印是屬性。要求集合中只能儲存兩個元素,使用三種方式遍歷。 // 重寫 toString 和hashcode 通過屬性去重 import java.util.HashSet; import java.util.Iterator; import java.util.Set; public class SetDemo2 { public static void main(String[] args) { Set<Person> ps = new HashSet<>(); ps.add(new Person("張三", 18, '男')); ps.add(new Person("李四", 20, '女')); ps.add(new Person("張三", 18, '男')); System.out.println(ps); } } class Person{ String name; int age; char gender; public Person() { } public Person(String name,int age, char gender) { this.name = name; this.age = age; this.gender = gender; } @Override public String toString() { return "Person [name=" + name + ", age=" + age + ", gender=" + gender + "]"; } @Override public int hashCode() { final int prime = 31; int result = 1; result = prime * result + age; result = prime * result + gender; 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 (gender != other.gender) return false; if (name == null) { if (other.name != null) return false; } else if (!name.equals(other.name)) return false; return true; } }
-
Set生成不重複隨機數
import java.util.HashSet; import java.util.Random; import java.util.Set; public class SetDemo3 { public static void main(String[] args) { Random r = new Random(); Set<Integer> set = new HashSet<>(); while (set.size() != 10) { int i = r.nextInt(20) + 1; set.add(i); } System.out.println(set); } }
-
利用Set實現List去重。
import java.util.ArrayList; import java.util.HashSet; import java.util.List; import java.util.Set; public class SetDemo4 { public static void main(String[] args) { List<String> list = new ArrayList<> (); list.add("大哥"); list.add("二哥"); list.add("大哥"); list.add("三哥"); System.out.println(distinct(list)); } public static List<String> distinct(List<String> list){ Set<String> set = new HashSet<> (); // 將list元素新增set去重 set.addAll(list); // 清空list list.clear(); // 將去重set中元素新增list中 list.addAll(set); return list; } }
8.Map
-
Map是雙列集合根介面。
-
將鍵對映到值的物件
-
一個對映不能包含重複的鍵。
-
每個鍵最多隻能對映到一個值key=value
-
Map介面和Collection介面的不同,Map是雙列的,Collection是單列的。
-
Map的鍵唯一,Collection的子體系Set是唯一的。
-
Map集合的資料結構值針對鍵有效,跟值無關。
-
Map分類
HashMap: key不能重複,但是可以為null,不能保證key存入和取出順序。 LinkedHashMap:可以保證key存入和取出的順序。
-
Map中方法
put(k key, v value) 新增元素 remove(Object key) 移除元素 對應鍵值對 void clear() 清空map boolean containsKey(Object key) 是否包含key boolean containsValue(Object value) 是否包含value boolean isEmpty() 是否為空(長度是否為0) int size() 鍵值對的個數
-
示例:
import java.util.HashMap; import java.util.Map; public class MapDemo1 { public static void main(String[] args) { Map<Integer,String> map = new HashMap<>(); map.put(5, "數字5"); map.put(6, "數字6"); map.put(7, "數字7"); String result1 = map.put(8, "數字8"); System.out.println(result1);// null String result2 = map.put(7, "number seven"); System.out.println(result2);// 數字7 System.out.println(map);// {5=數字5, 6=數字6, 7=數字7} System.out.println(map.remove(9));// null System.out.println(map.remove(7));// number seven System.out.println(map.containsKey(7));//false System.out.println(map.containsValue("數字6"));// true map.clear(); System.out.println(map.isEmpty());// true } }
-
HashMap遍歷
import java.util.Collection; import java.util.HashMap; import java.util.Map; import java.util.Set; public class MapCDemo2 { public static void main(String[] args) { Map<Integer,String> map = new HashMap<>(); map.put(1, "one"); map.put(2, "two"); map.put(3, "three"); map.put(4, "four"); // 1.map遍歷方式:獲取所有key keySet: // 獲取所有key Set<Integer> keySet = map.keySet(); for (Integer key : keySet) { // 迴圈所有key,通過get方法列印所有value System.out.println(map.get(key)); } // 2.map遍歷方式:獲取所有鍵和值 entrySet Set<Map.Entry<Integer,String>> entrySet = map.entrySet(); for (Map.Entry<Integer, String> entry : entrySet) { System.out.println(entry.getKey() + ":" +entry.getValue()); } // 3.map遍歷方式:獲取所有value values Collection<String> values = map.values(); for (String s : values) { System.out.println(s); } } }
- 上述遍歷方式也可以通過迭代器寫
import java.util.Map.Entry; import java.util.Iterator; Iterator<Entry<Integer,String>> it = entrySet.iterator(); while(it.hasNext()) { Entry<Integer,String> entry = it.next(); System.out.println(entry.getKey() + ":" + entry.getValue()); }
-
練習:統計字串個數:
import java.util.HashMap; import java.util.Map; import java.util.Scanner; public class MapDemo3 { public static void main(String[] args) { Map<Character,Integer> map = new HashMap<>(); Scanner sc = new Scanner(System.in); System.out.println("請輸入字串:"); String str = sc.next(); for (int i=0;i<str.length();i++) { char ch = str.charAt(i); // 根據key去map中取value,如果有值就返回value,如果沒有返回預設值。 Integer count = map.getOrDefault(ch, 0); count++; map.put(ch, count); // Integer count = map.get(ch); // if (count == null) { // // 字元第一處出現 // map.put(ch, 1); // }else { // // 不是第一次出現 // count++; // map.put(ch, count); // } } System.out.println(map); } } // 請輸入字串: // asdaerteatsfcx // {a=3, r=1, s=2, c=1, d=1, t=2, e=2, f=1, x=1}
-
HashMap實現原理:
-
HashMap是通過雜湊表(散列表)實現的。 陣列+連結串列。
Map map = new HashMap(); // 它的底層是陣列+連結串列,主體是陣列。 當執行map.put(1,a); key=1 首先求出hashCode, 對hashCode進行hash運算,運算結果代表它儲存陣列中的位置(bucket)。 但是當陣列儲存bucket位置中已經存在元素(hash相同,存在hash衝撞),它會對比它們之間key,如果不相同,它會用連結串列連線當前位置所有元素,後進來元素放在頭上(頭插法)。如果比較key相同,就把對應value值進行替換。
-