Hash表数据结构
-
为什么哈希表的随机增删,以及查询效率都很高?
- 增删是在链表上完成。
- 查询也不需要都扫描,只需要部分扫描。
-
重点:通过讲解可以得出HashMap集合的key,会先后调用两个方法,一个方法是hashCode(),一个方法是equal(),那么这两个方法都需要重写。
-
package com.lichennan.collection; import java.util.HashMap; import java.util.Map; import java.util.Set; /* HashMap集合 1.HashMap集合是底层是哈希表/散列表的数据结构 2.哈希表是一个数组和单向链表的结合体。 3.HashMap集合底层的源代码: publi class HashMap{ //HashMap底层实际上就是一个数组 Node<K,V>[] table; //静态的内部类HashMap.Node static class Node<K,V>{ final int hash; 哈希值 final K key; 存储到map集合中的那个key V value 存储到map集合中的那个value Node<K,V> next; 下一个节点的内存地址 } } 哈希表/散列表: 一维数组,这个数组中每一个元素是一个单向链表。(数组和链表的结合体) 4.最主要掌握的是: map.put(k,v) v=map.get(k) 以上两个方法的实现原理,需要掌握 5.HashMap集合的key部分特点 无序不可重复 6.HashMap集合的默认初始化容量是16,默认加载因子是0.75 这个默认加载因子是当HashMap集合底层数组的容量达到75%的时候,数组开始扩容。 */ public class HashMapTest01 { public static void main(String[] args) { Map<Integer,String> map = new HashMap<>(); //测试HashMap集合Key部分的元素特点 //Integer是key,它的hashCode和equal都重写了 map.put(1111,"张三"); map.put(6666,"lisi"); map.put(7777,"wangwu"); map.put(2222,"liusan"); map.put(2222,"king"); //key重复的时候value会自动覆盖 System.out.println(map.size()); //遍历map集合 Set<Map.Entry<Integer,String>> set = map.entrySet(); for (Map.Entry<Integer,String> entry:set) { //key部分元素无序不可重复 System.out.println(entry.getKey()+"="+entry.getValue()); } } }
重写hashCode(),equal()方法
package com.lichennan.collection;
import java.util.Objects;
public class Student {
private String name;
public Student(){
}
public Student(String name) {
this.name = name;
}
public String getName(){
return name;
}
public void setName(String name){
this.name = name;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Student student = (Student) o;
return Objects.equals(name, student.name);
}
@Override
public int hashCode() {
return Objects.hash(name);
}
}
package com.lichennan.collection;
import java.util.HashSet;
import java.util.Set;
/*向Map集合中存,以及map集合中取,都是先调用key的hashCode方法,然后再调用equals方法!
equals方法有可能调用,也有可能不调用。
注意:如果一个类的equals方法重写了,那么hashCode()方法必须重写
*/
public class HashMapTest02 {
public static void main(String[] args) {
Student s1 = new Student("zhangsan");
Student s2 = new Student("zhangsan");
//重写equals方法之前是false
// System.out.println(s1.equals(s2)); //false
//重写equals方法之前是ture
System.out.println(s1.equals(s2));
System.out.println("s1的hashCode="+s1.hashCode());
System.out.println("s2的hashCode="+s2.hashCode());
Set<Student> students = new HashSet<>();
students.add(s1);
students.add(s2);
System.out.println(students.size());//无序不可重复,所以结果是1
}
}