简单哈希表的改进
简单哈希表
基于数组实现的简单哈希表,使用取模法处理哈希冲突(就是发生冲突时直接替代)
public class HashTable<E> {
// 哈希表的初始容量,使用质数可减少哈希冲突
private final int TABLE_SIZE = 10;
// 使用Object数组存储元素,需进行类型转换
private final Object[] TABLE = new Object[TABLE_SIZE];
public void insert(E obj) {
// 计算元素在数组中的存储位置
int index = hash(obj);
// 直接存储元素,冲突时会覆盖原有值
TABLE[index] = obj;
}
public boolean contains(E obj) {
// 计算元素理论上的存储位置
int index = hash(obj);
// 使用引用相等判断元素是否存在(非值相等)
return TABLE[index] == obj;
}
private int hash(E obj) {
// 获取对象原始哈希码
int hashCode = obj.hashCode();
// 取模运算确保索引在数组范围内
return hashCode % TABLE_SIZE;
}
}以下是改进的哈希表:
基于链地址法(拉链法)实现的哈希表。
每个哈希槽位存储一个链表头节点,冲突元素通过链表连接(依次存储在链表当中),这样就可以解决上面发生元素冲突时覆盖的问题了
public class HashTable<E> {
// 哈希表初始容量
private final int TABLE_SIZE = 10;
// 存储链表头节点的数组,使用泛型数组需通过强制类型转换创建
private final Node<E>[] TABLE = new Node[TABLE_SIZE];
/**
* 构造函数初始化哈希表
* 为每个槽位创建哑元头节点,减少插入删除时的边界判断
*/
public HashTable() {
for (int i = 0; i < TABLE_SIZE; i++)
TABLE[i] = new Node<>(null); // 创建哑元头节点
}
public void insert(E obj) {
int index = hash(obj); // 计算哈希值
Node<E> head = TABLE[index]; // 获取槽位的头节点
Node<E> node = new Node<>(obj); // 创建新节点
// 头插法插入新节点
node.next = head.next;
head.next = node;
}
public boolean contains(E element) {
int index = hash(element); // 计算哈希值
Node<E> node = TABLE[index].next; // 获取第一个有效节点
// 遍历链表查找元素
while (node != null) {
if (node.element == element) // 使用引用相等判断
return true;
node = node.next;
}
return false;
}
/**
* 返回哈希表的字符串表示形式
* 格式:每个槽位的链表元素用"->"连接,槽位间用换行分隔
*/
@Override
public String toString() {
StringBuilder builder = new StringBuilder();
for (int i = 0; i < TABLE_SIZE; i++) {
Node<E> head = TABLE[i].next; // 获取第一个有效节点
while (head != null) {
builder.append(head.element).append("->");
head = head.next;
}
builder.append("\n"); // 槽位结束添加换行
}
return builder.toString();
}
private int hash(E obj) {
int hashCode = obj.hashCode();
return hashCode % TABLE_SIZE; // 取模运算确保索引合法
}
/**
* 链表节点类,存储元素和指向下一个节点的引用
*/
private static class Node<E> {
private final E element; // 节点存储的元素
private Node<E> next; // 指向下一个节点的引用
public Node(E element) {
this.element = element;
}
}
} 版权申明
本文系作者 @吃了一只小羊 原创发布在Hello World站点。未经许可,禁止转载。
暂无评论数据