类架构
分离链接散列表的类结构
package cn.edut.hash;
import java.util.List;
public class SeparateChainingHashTable <T>{
/** * 构造 * 使用默认大小 */
public SeparateChainingHashTable() {
// TODO Auto-generated constructor stub
}
/** * 构造 * 设定大小, * @param size */
public SeparateChainingHashTable(int size) {
// TODO Auto-generated constructor stub
}
/** * 添加 元素 * @param e */
public void insert(T e) {
// TODO Auto-generated method stub
}
/** * 删除 元素 * @param e */
public void remove(T e) {
// TODO Auto-generated method stub
}
/** * 判断是否包含元素 * @return */
public boolean contains() {
// TODO Auto-generated method stub
return false ;
}
/** * 清空散列 */
public void makeEmpty() {
// TODO Auto-generated method stub
}
/** * 需要是一个素数 */
private static final int DEFAULT_TABLE_SIZE = 101 ;
/** * list里面放链表,根据hashcode判断放在哪个链表里面 */
private List<T>[] keyList ;
/** * 存量多少个数据 */
private int currentSize ;
/** * 扩容 */
private void rehash() {
// TODO Auto-generated method stub
}
/** * 计算元素hashcode * @return */
private int myhash(T e) {
// TODO Auto-generated method stub
return 0 ;
}
/** * 生产下一个素数 * 是否要静态? */
private long nextPrime(int n) {
// TODO Auto-generated method stub
return 0 ;
}
/** * 判断素数 * 是否要静态? */
private boolean isPrime(int n ) {
// TODO Auto-generated method stub
return false ;
}
}
上面架构的实现
package cn.edut.algorithm;
import static org.junit.Assume.assumeNotNull;
public class SeparateChainingHashTable<K , V> {
/** * 构造 使用默认大小 */
public SeparateChainingHashTable() {
this(DEFAULT_TABLE_SIZE);
}
/** * 构造 设定大小, * * @param size */
@SuppressWarnings("unchecked")
public SeparateChainingHashTable(int size) {
table = new Entry[size];
}
public int size() {
return size ;
}
/** * 删除 元素 * * @param e */
public void remove(K key) {
int hash = hash(key);
int index = indexFor(hash , table.length);
Entry<K, V> preEntry =null;
for(Entry<K, V> e=table[index] ; e!=null ; e=e.next) {
if((e.key.equals(key) || e.key == key) && hash==e.hash) {
if(preEntry!= null) {
preEntry.next = e.next ;
}else {
//只有一个节点
table[index] = null;
}
size--;
}
preEntry = e;
}
}
/** * 判断是否包含元素 * * @return */
public boolean contains(K key) {
Entry<K, V> entry = getEntry(key);
return entry!=null;
}
/** * 清空散列 */
public void makeEmpty() {
for (int i = 0; i < table.length; i++) {
Entry<K, V> t = table[i] ;
table[i] = null ;
while(t!=null) {
Entry<K, V> next = t.next ;
t.clear();
t = next ;
}
}
this.size = 0 ;
}
public V get(K key) {
Entry<K, V> entry = getEntry(key);
return entry!=null?entry.value : null ;
}
/* ---------------- Fields -------------- */
/** * 需要是一个素数 */
private static final int DEFAULT_TABLE_SIZE = 3;
/** * list里面放链表,根据hashcode判断放在哪个链表里面 */
private Entry<K, V>[] table;
/** * 存量多少个数据 */
private int size;
/** * 扩容 */
private void rehash() {
// TODO Auto-generated method stub
}
private Entry<K, V> getEntry(K key) {
int hash = key==null?0 : hash(key);
int index = indexFor(hash , table.length);
for(Entry<K, V> e=table[index] ; e!=null ; e= e.next) {
K k = e.key;
if(k==key || (k!=null && k.equals(key))) {
return e;
}
}
return null;
}
/** * 计算元素hashcode * * @return */
private int hash(K e) {
int h = e.hashCode() ;
h ^= (h >> 20 )^(h >>12) ;
return h^(h >> 8) ^ (h >> 4 );
}
private int indexFor(int h , int size) {
return h%size;
}
/** * 生产下一个素数 是否要静态? */
private long nextPrime(long n) {
while(isPrime(++n)) {}
return n;
}
/** * 判断素数 是否要静态? */
private boolean isPrime(long n) {
if (n < 2) {
return false;
} else if (n > 2) {
if(n%2==0) {
return false ;
}else {
long len = (long) Math.sqrt(n);
for(long i=3 ; i < len ;i++) {
if(n%i==0) {
return false;
}
}
}
}
return true;
}
private void addEntry(K key, V value, int hash, int index) {
if(size>=table.length/2 && table[index]!=null ) {
resize((int) nextPrime(table.length*2));
index= indexFor(hash, table.length);
}
Entry<K, V> entry = new Entry<>(table[index], hash, value, key);
table[index] = entry ;
size++;
}
private void resize(int newSize) {
Entry<K, V>[] oldTable = table;
Entry[] newTable = new Entry[newSize];
transfer(newTable);
table = newTable;
}
private void transfer(Entry[] newTable) {
for (Entry<K,V> e : table) {
while(e!=null) {
Entry<K, V> next = e.next;
int index = indexFor(e.hash , newTable.length);
e.next = newTable[index];
newTable[index] = e ;
e = next;
}
}
}
/** * 添加 元素 * * @param e */
public V insert(K key , V value) {
int hash = key==null?0:hash(key);
int index = indexFor(hash , table.length);
Entry<K, V> e = table[index];
//桶上有元素,覆盖
while (e!=null) {
if( e.hash == hash && (e.key==key || e.key.equals(key))) {
V oldValue = e.value ;
e.value = value ;
return oldValue ;
}
e = e.next ;
}
//添加节点
addEntry(key,value,hash,index);
return null;
}
private static class Entry<K,V> {
private Entry<K, V> next ;
private int hash ;
private V value ;
private K key ;
public Entry(Entry<K, V> next, int hash, V value, K key) {
super();
this.next = next;
this.hash = hash;
this.value = value;
this.key = key;
}
public void clear() {
next = null;
hash = 0 ;
value = null;
key = null;
}
}
@Override
public String toString() {
StringBuilder sb = new StringBuilder();
sb.append("[ ") ;
for (Entry<K, V> e : table) {
while (e!=null) {
sb.append(e.key) ;
sb.append(":");
sb.append(e.value);
sb.append(", ");
e = e.next ;
}
}
sb.delete(sb.length()-", ".length(), sb.length());
sb.append("]") ;
return sb.toString();
}
}