散列表的相關內容

基於鏈表法解決哈希衝突的實現

該拉鍊發採用了一般性的策略,爲M個元素分別構建符號表來保存散列值到這裏的建。該代碼是摘自算法(第四版)。

public class SequentialSearchST<Key, Value> {
    private Node first;//鏈表首結點
	private class Node{
		//鏈表結點的定義
		private final Key key;
		private Value val;
		private Node next;
		
		public Node(Key key, Value val, Node next) {
			this.key = key;
			this.val = val;
			this.next = next;
		}
		public Key getKey() {
			return key;
		}
 
		public Value getVal() {
			return val;
		}
 
		public void setVal(Value val) {
			this.val = val;
		}
 
		public Node getNext() {
			return next;
		}
 
		public void setNext(Node next) {
			this.next = next;
		}
		
	}
	//查找給定的鍵,返回相關聯的值
	public Value get(Key key) {
		for(Node i = first; i != null; i = i.next) {
            if(key.equals(i.key))
            	return i.val;
		}
		return null;
	}
	//查找給定的鍵,找到則更新其值,否則在表中新建結點
	public void put(Key key, Value val) {
		for(Node i = first; i != null; i = i.next) {
			if(key.equals(i.key)) {
				i.val = val;
				return;
			}
		}
		first = new Node(key, val, first);
	}
	//刪除結點
	public void delete(Key key) {
		first = delete(first, key);
	}
	private Node delete(Node x, Key key) {
		if(x == null) {
			return null;
		}
		if(key.equals(x.key)) {
			return x.next;
		}
		x.next = delete(x.next, key);
		return x;
	}
	public Iterable<Key> keys(){
		Queue<Key> q = new Queue<Key>();
		for(Node i = first;  i != null; i = i.next) {
			q.enqueue(i.key);
		}
		return q;
	}
	public Key getKey() {
		return first.key;
	}
}
public class SeparateChainingHashST<Key, Value> {
	//SequetialSearchST
	private int N;//鍵值對總數
	private int M;//散列表的大小
	private SequentialSearchST<Key, Value>[] st;//存放鏈表對象的數組
    public SeparateChainingHashST() {//默認的構造函數會使用997條鏈表
    	this(997);
    }
    public SeparateChainingHashST(int M) {
    	//創建M條鏈表
    	this.M = M;
    	//創造一個(SequentialSearchST<Key, Value>[])類型的,長度爲M的數組
    	st = (SequentialSearchST<Key, Value>[]) new SequentialSearchST[M];
    	for(int i = 0; i < M; i++) {
    		//爲每一個數組元素申請一個空間
    		st[i] = new SequentialSearchST();
    	}
    }
    private int hash(Key key) {
    	return (key.hashCode() & 0x7fffffff) % M;
    }
    public Value get(Key key) {
    	return (Value)st[hash(key)].get(key);
    }
    public void put(Key key, Value val) {
    	st[hash(key)].put(key, val);
    }
    public void delete(Key key) {
    	st[hash(key)].delete(key);
    }
    public Iterable<Key> keys(){
    	Queue<Key> queue = new Queue<Key>();
    	for(int i = 0; i < M; i++) {
    		System.out.println("第" + i +"個元素的鏈表");
    		for(Key key : st[i].keys()) {
    			queue.enqueue(key);
    			System.out.print(key + " " + get(key) + " ,");
    		}
    		System.out.println();
    	}
    	return queue;
    }
    public static void main(String[] args) {
    	SeparateChainingHashST<String, Integer> st = new SeparateChainingHashST<String, Integer>(5);
        for (int i = 0; i < 13; i++) {
            String key = StdIn.readString();
            st.put(key, i);
        }
        for (String s : st.keys())
            StdOut.println(s + " " + st.get(s));
        st.delete("M");
        StdOut.println("*************************************");
        for (String s : st.keys()) {
        	 StdOut.println(s + " " + st.get(s));
        }
    }
}

實現一個LRU緩存淘汰算法

採用一個鏈表來保存訪問的數據,每次有新數據時看是否匹配已有的,有則將以保存的數據放到最前端,沒有則將新數據保存至最前端。如果內存滿了則從最末端刪除數據。


public class LRULinkedHashMap<K, V> extends LinkedHashMap<K, V> {  
    private final int maxCapacity;  

    private static final float DEFAULT_LOAD_FACTOR = 0.75f;  

    private final Lock lock = new ReentrantLock();  

    public LRULinkedHashMap(int maxCapacity) {  
        super(maxCapacity, DEFAULT_LOAD_FACTOR, true);  
        this.maxCapacity = maxCapacity;  
    }  

    @Override 
    protected boolean removeEldestEntry(java.util.Map.Entry<K, V> eldest) {  
        return size() > maxCapacity;  
    }  
    @Override 
    public boolean containsKey(Object key) {  
        try {  
            lock.lock();  
            return super.containsKey(key);  
        } finally {  
            lock.unlock();  
        }  
    }  


    @Override 
    public V get(Object key) {  
        try {  
            lock.lock();  
            return super.get(key);  
        } finally {  
            lock.unlock();  
        }  
    }  

    @Override 
    public V put(K key, V value) {  
        try {  
            lock.lock();  
            return super.put(key, value);  
        } finally {  
            lock.unlock();  
        }  
    }  

    public int size() {  
        try {  
            lock.lock();  
            return super.size();  
        } finally {  
            lock.unlock();  
        }  
    }  

    public void clear() {  
        try {  
            lock.lock();  
            super.clear();  
        } finally {  
            lock.unlock();  
        }  
    }  

    public Collection<Map.Entry<K, V>> getAll() {  
        try {  
            lock.lock();  
            return new ArrayList<Map.Entry<K, V>>(super.entrySet());  
        } finally {  
            lock.unlock();  
        }  
    }  
}  
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章