java数据结构——哈希表(HashTable)
哈希表提供了快速的插入操作和查找操作,每一个元素是一个key-value对,其基于数组来实现。
一、Java中HashMap与Hashtable的区别:
HashMap可以接受null键值和值,而Hashtable则不能。
Hashtable是线程安全的,通过synchronized实现线程同步。而HashMap是非线程安全的,但是速度比Hashtable快。
这两个类有许多不同的地方,下面列出了一部分:
a) Hashtable 是 JDK 1 遗留下来的类,而 HashMap 是后来增加的。
b)Hashtable 是同步(synchronized)的,比较慢,但 HashMap 没有同步策略,所以会更快。
c)Hashtable 不允许有个空的 key,但是 HashMap 允许出现一个 null key。
- public class Employee {
- private String key;
- private String name;
- public String getKey() {
- return key;
- }
- public void setKey(String key) {
- this.key = key;
- }
- public String getName() {
- return name;
- }
- public void setName(String name) {
- this.name = name;
- }
- public Employee(String key, String name) {
- this.key = key;
- this.name = name;
- }
- }
员工类
- import java.math.BigInteger;
- public class HashTable {
- private Employee[] arr;
- public HashTable() {
- arr = new Employee[1000];
- }
- public HashTable(int Maxsize) {
- arr = new Employee[Maxsize];
- }
- // public void Insert(Employee emplo) {//以整型作为索引
- // arr[emplo.getKey()] = emplo;
- // }
- public void Insert(Employee emplo) {// 以字符串作为索引
- arr[hashTable(emplo.getKey())] = emplo;
- }
- // public Employee Find(int key) {
- // return arr[key];
- // }
- public Employee Find(String key) {
- return arr[hashTable(key)];
- }
- public int hashTable(String key) {// 转换AscII码存储,但存在码值重复问题
- BigInteger hashVal = new BigInteger("0");
- BigInteger pow27 = new BigInteger("1");
- // int hashVal = 0;
- int i = key.length() - 1;
- // int pow27 = 1;// 27^0
- // for (; i >= 0; i--) {
- // int letter = key.charAt(i) - 96;
- // hashVal += letter;
- // }
- // return hashVal;
- // }
- for (; i >= 0; i--) {
- int letter = key.charAt(i) - 96;
- BigInteger letterB = new BigInteger(String.valueOf(letter));
- hashVal = hashVal.add(letterB.multiply(pow27));// hashVal += letter * pow27;
- // hashVal += letter * pow27;// 这里会溢出
- // pow27*=27
- pow27 = pow27.multiply(new BigInteger(String.valueOf(27)));
- }
- //return hashVal % arr.length;
- return hashVal.mod(new BigInteger(String.valueOf(arr.length))).intValue();
- }
- }
方法类
- public class Demo {
- public static void main(String[] args) {
- HashTable ht = new HashTable();
- /*ht.Insert(new Employee(1, "Ally"));
- ht.Insert(new Employee(2, "Jion"));
- ht.Insert(new Employee(3, "Micale"));
- ht.Insert(new Employee(4, "Lily"));
- System.out.println(ht.Find(2).getName());*/
- ht.Insert(new Employee("aka", "74"));
- System.out.println(ht.Find("aka").getName());
- }
- }
演示类
链地址法
- public class LinkList {
- private Node first;// 火车头,保存头结点的一个指向
- public LinkList() {// 初始化
- first = null;
- }
- public Node deleteFirst() {// 删除头结点
- first = first.next;// 头结点为头结点的下一个
- return first;
- }
- public Node find(String key) {// 按值查找,返回null或索引值
- Node current = first;// 从头结点开始
- while (!key.equals(current.emplo.getKey())) {
- if (current.next == null) {// 尾结点后继为null
- return null;
- }
- current = current.next;
- }
- return current;// 找到返回
- }
- public Node delete(String key) {// 删除任意结点
- Node current = first;
- Node previous = first;
- while (!key.equals(current.emplo.getKey())) {//找到current返回true !true = false
- if (current.next == null) {// 没有找到
- return null;
- }
- previous = current;// 保存邻近的两个结点
- current = current.next;
- }
- if (current == first) {// 第一个结点
- first = first.next;
- } else {// 后面的结点
- previous.next = current.next;// 上一个结点的下一个变为当前结点的下一个,当前结点删除
- }
- return current;// 结点类,返回结点类型
- }
- public void insert(Employee emplo) {// 在头结点之后插入
- Node node = new Node(emplo);// 创建新的结点
- // 这里深深体会一下精妙之处,first保存着一个指向
- node.next = first;// 图示第一步
- first = node;// 图示第二步
- }
- }
链表
- public class Node {// 包装车厢
- /**
- * 链结点
- */
- public Employee emplo;// 数据域
- public Node next;// 指针域,后指针
- public Node(Employee emplo) {// 构造函数
- this.emplo = emplo;
- }
- }
结点
- import java.math.BigInteger;
- public class HashTable {
- private LinkList[] arr; // 每个数值对应一个链表
- public HashTable() {
- arr = new LinkList[100];
- }
- public HashTable(int Maxsize) {
- arr = new LinkList[Maxsize];
- }
- public void Insert(Employee emplo) {// 以字符串作为索引
- String key = emplo.getKey();
- int hashVal = hashTable(key);
- if (arr[hashVal] == null) {
- arr[hashVal] = new LinkList();
- }
- arr[hashVal].insert(emplo);
- }
- public Employee Find(String key) {
- int hashVal = hashTable(key);
- return arr[hashVal].find(key).emplo;
- }
- public Employee Delete(String key) {
- int hashVal = hashTable(key);
- return arr[hashVal].delete(key).emplo;
- }
- public int hashTable(String key) {// 转换AscII码存储,但存在码值重复问题
- BigInteger hashVal = new BigInteger("0");
- BigInteger pow27 = new BigInteger("1");
- int i = key.length() - 1;
- for (; i >= 0; i--) {
- int letter = key.charAt(i) - 96;
- BigInteger letterB = new BigInteger(String.valueOf(letter));
- hashVal = hashVal.add(letterB.multiply(pow27));
- pow27 = pow27.multiply(new BigInteger(String.valueOf(27)));
- }
- return hashVal.mod(new BigInteger(String.valueOf(arr.length))).intValue();
- }
- }
方法
- public class Demo {
- public static void main(String[] args) {
- HashTable ht = new HashTable();
- /*ht.Insert(new Employee(1, "Ally"));
- ht.Insert(new Employee(2, "Jion"));
- ht.Insert(new Employee(3, "Micale"));
- ht.Insert(new Employee(4, "Lily"));
- System.out.println(ht.Find(2).getName());*/
- ht.Insert(new Employee("a", "Jack")); // 开放地址法
- ht.Insert(new Employee("ct","Rose"));
- ht.Insert(new Employee("b", "Upon"));
- System.out.println(ht.Find("a").getName());//打印对象
- System.out.println(ht.Find("ct").getName());
- System.out.println(ht.Find("b").getName());
- System.out.println(ht.hashTable("a"));
- System.out.println(ht.hashTable("ct"));
- }
- }
测试
参考文献:
https://www.cnblogs.com/aeolian/p/8468632.html
https://www.cnblogs.com/williamjie/p/9099141.html
http://www.luyixian.cn/news_show_10979.aspx
java数据结构——哈希表(HashTable)的更多相关文章
- Java中哈希表(Hashtable)是如何实现的
Java中哈希表(Hashtable)是如何实现的 Hashtable中有一个内部类Entry,用来保存单元数据,我们用来构建哈希表的每一个数据是Entry的一个实例.假设我们保存下面一组数据,第一列 ...
- java数据结构----哈希表
1.哈希表:它是一种数据结构,可以提供快速的插入操作和查找操作.如果哈希表中有多少数据项,插入和删除操作只需要接近常量的时间.即O(1)的时间级.在计算机中如果需要一秒内查找上千条记录,通常使用哈希表 ...
- JAVA数据结构--哈希表的实现(分离链接法)
哈希表(散列)的定义 散列表(Hash table,也叫哈希表),是根据关键码值(Key value)而直接进行访问的数据结构.也就是说,它通过把关键码值映射到表中一个位置来访问记录,以加快查找的速度 ...
- java集合-哈希表HashTable
一.简介 HashTable也是一种key-value结构,key-value不允许null,并且这个类的几乎全部的方法都加上了synchronized锁,来保证并发安全,由于加了锁所以性能方面会比较 ...
- Java数据结构——哈希表
- 哈希表(hashtable)的javascript简单实现
javascript中没有像c#,java那样的哈希表(hashtable)的实现.在js中,object属性的实现就是hash表,因此只要在object上封装点方法,简单的使用obejct管理属性的 ...
- C#中哈希表(HashTable)的用法详解以及和Dictionary比较
1. 哈希表(HashTable)简述 在.NET Framework中,Hashtable是System.Collections命名空间提供的一个容器,用于处理和表现类似keyvalue的键值对, ...
- 数据结构 -- 哈希表(hash table)
简介 哈希表(Hash table,也叫散列表),是根据关键码值(Key value)而直接进行访问的数据结构.也就是说,它通过把关键码值映射到表中一个位置来访问记录,以加快查找的速度.这个映射函 ...
- 哈希表(Hashtable)简述
一,哈希表(Hashtable)简述 在.NET Framework中,Hashtable是System.Collections命名空间提供的一个容器,用于处理和表现类似keyvalue的键值对,其中 ...
随机推荐
- TensorFlow Object Detection API 迁移学习
https://blog.csdn.net/ctwy291314/article/details/80999645 https://www.cnblogs.com/gmhappy/p/9472361. ...
- Spring学习之旅(一)--初始Spring
之前从博客.视频断断续续的学到了 Spring 的相关知识,但是都是一个个碎片化的知识.刚好最近在读 <Sprign实战(第四版)>,所以借此机会重新整理下Spring 系列的内容. Sp ...
- 关于line-height 行高的一些理解和技巧
大家都知道,如何设置文字垂直居中,也就是:设置line-height 和 外围盒子的高度height一致: 其实这里有个地方,是多余的,也就是height,设不设置都居中: 那么,行高是生产高度的? ...
- 特殊字符处理 java-jsp
public String dealStr(String name){ String newStr=""; if(name != null && name.leng ...
- 证书pfx转jks
keytool -importkeystore -srckeystore 2756649_order.hanels-home.com.pfx -srcstoretype pkcs12 -destke ...
- SCRUM术语
http://www.scrumcn.com/agile/scrum-knowledge-library/scrum.html#tab-id-2 Scrum: Scrum无对应中文翻译 Agile: ...
- UOJ 34 多项式乘法 FFT 模板
这是一道模板题. 给你两个多项式,请输出乘起来后的多项式. 输入格式 第一行两个整数 nn 和 mm,分别表示两个多项式的次数. 第二行 n+1n+1 个整数,表示第一个多项式的 00 到 nn 次项 ...
- JSP内置对象(一)
一.out对象out对象是JspWriter类的实例,是向客户端输出内容常用的对象1.void println() out的println()方法,向客户端打印字符串 2. void clear() ...
- Day004作业
1,写代码,有如下列列表,按照要求实现每⼀一个功能li = ["alex", "WuSir", "ritian", "barry& ...
- 代码质量检测(SonarQube)整合中文版+阿里P3C
代码质量检测(SonarQube)整合中文版+阿里P3C 简介 SonarQube是一种自动代码审查工具,用于检测代码中的错误,漏洞和代码异味.它可以与您现有的工作流程集成,以便在项目分支和拉取请求之 ...