LRU算法实现:
package com.javaeye.xiaobian.jgroups; import java.util.LinkedHashMap; import java.util.Set; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; public class LRUCache<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 LRUCache(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; } /** * Weather contains someone Object according to a key * * @param key */ @Override public boolean containsKey(Object key) { lock.lock(); try { return super.containsKey(key); } finally { lock.unlock(); } } /** * Get one Object according to a key * * ��ȡ@param key */ @Override public V get(Object key) { lock.lock(); try { return super.get(key); } finally { lock.unlock(); } } /** * Put an Object to cache * * @param key,valueӻ��� */ @Override public V put(K key, V value) { lock.lock(); try { return super.put(key, value); } finally { lock.unlock(); } } /** * The cache's size */ public int size() { lock.lock(); try { return super.size(); } finally { lock.unlock(); } } /** * clear the cache * */ public void clear() { lock.lock(); try { super.clear(); } finally { lock.unlock(); } } /** * Delete one Object from cache * * @param key */ public void delete(Object key) { lock.lock(); try { super.remove(key); } finally { lock.unlock(); } } /** * Delete some Objects from cache * * @param objArrs */ public void batchDelete(Object[] objArrs) { lock.lock(); try { for (int i = 0; i < objArrs.length; i++) { delete(objArrs[i]); } } finally { lock.unlock(); } } /** * Get all Objects from cache * * @return Set */ public Set getAll() { lock.lock(); try { return this.entrySet(); } finally { lock.unlock(); } } /** * Update one Object in the Cache * * @param key * @param value */ public void update(K key, V value) { lock.lock(); try { super.remove(key); this.put(key, value); } finally { lock.unlock(); } } }
利用Jgroups实现集群同步:
package com.javaeye.xiaobian.jgroups; import java.io.Serializable; import org.jgroups.Channel; import org.jgroups.ExtendedReceiverAdapter; import org.jgroups.JChannel; import org.jgroups.Message; public class CacheSynchronizer { private static String protocolStackString = "UDP(mcast_addr=236.11.11.11;mcast_port=32767;ip_ttl=64;" + "mcast_send_buf_size=32000;mcast_recv_buf_size=64000):" + "PING(timeout=2000;num_initial_members=3):" + "MERGE2(min_interval=5000;max_interval=10000):" + "FD_SOCK:" + "VERIFY_SUSPECT(timeout=1500):" + "pbcast.NAKACK(gc_lag=50;retransmit_timeout=300,600,1200,2400,4800):" + "pbcast.STABLE(desired_avg_gossip=20000):" + "UNICAST(timeout=2500,5000):" + "FRAG:" + "pbcast.GMS(join_timeout=5000;join_retry_timeout=2000;shun=false;print_local_addr=false)"; private static String groupName = "CACHEGROUP"; private Channel channel = null; private ReceiveCallback recvCallback = null; // inner class ,receive the broadcast and handle private class ReceiveCallback extends ExtendedReceiverAdapter { private Cache cache = null; public void setCache(Cache baseCache) { cache = baseCache; } public void receive(Message msg) { if (cache == null) return; CacheMessage message = (CacheMessage) msg.getObject(); Object key = message.getKey(); Object value = message.getValue(); if (message.getOperation() == CacheConstants.CLUSTER_ENTRY_ADD) { cache.put(key, value); } else if (message.getOperation() == CacheConstants.CLUSTER_ENTRY_DELETE) { cache.delete(key); } else if (message.getOperation() == CacheConstants.CLUSTER_ENTRY_DELETE_SOME) { cache.batchDelete((Object[]) key); } else if (message.getOperation() == CacheConstants.CLUSTER_ENTRY_UPDATE) { cache.update(key, value); } } } public CacheSynchronizer(Cache cache) throws Exception { channel = new JChannel(protocolStackString); recvCallback = new ReceiveCallback(); recvCallback.setCache(cache); channel.setReceiver(recvCallback); channel.connect(groupName); } /** * Send broadcast message * * @param msg * @throws Exception */ public void sendCacheFlushMessage(Object msg) throws Exception { channel.send(null, null, (Serializable) msg); // 发送广播 } }
辅助类:
package com.javaeye.xiaobian.jgroups; public class CacheConstants { /** * Cluster add handle */ public final static int CLUSTER_ENTRY_ADD = 10; /** * Cluster update handle */ public final static int CLUSTER_ENTRY_UPDATE = 20; /** * Cluster delete handle */ public final static int CLUSTER_ENTRY_DELETE = 30; /** * Cluster delete sone handle */ public final static int CLUSTER_ENTRY_DELETE_SOME = 40; }
package com.javaeye.xiaobian.jgroups; import java.io.Serializable; public abstract class CacheMessage implements Serializable { public abstract int getOperation(); public abstract Object getKey(); public abstract Object getValue(); }
package com.javaeye.xiaobian.jgroups; import java.io.Serializable; public class SynCacheMessage extends CacheMessage implements Serializable { private Object key; private Object value; private int op; public SynCacheMessage() { } public SynCacheMessage(Object key, Object value, int op) { this.key = key; this.op = op; this.value = value; } public Object getKey() { return key; } public int getOperation() { return op; } public Object getValue() { return value; } }
实际使用的Cache类:
package com.javaeye.xiaobian.jgroups; import java.util.Collections; import java.util.Iterator; import java.util.Map; import java.util.Set; public class Cache { private static Cache singleton = null; private LRUCache lruCache = null; private CacheSynchronizer cacheSyncer = null; private Cache(int size) { lruCache = new LRUCache(size); createSynchronizer(); } public static Cache getInstance() { if (singleton == null) { singleton = new Cache(100000); } return singleton; } public CacheSynchronizer getSynchronizer() { return cacheSyncer; } public int size() { return lruCache.size(); } public void createSynchronizer() { try { cacheSyncer = new CacheSynchronizer(this); } catch (Exception e) { e.printStackTrace(); } } public void batchDelete(Object[] objArrs) { lruCache.batchDelete(objArrs); } public void delete(Object key) { lruCache.remove(key); } public void deleteAll() { lruCache.clear(); } public Object get(Object key) { return lruCache.get(key); } public void put(Object key, Object value) { lruCache.put(key, value); } public void update(Object key, Object value) { lruCache.update(key, value); } public Set getAll() { return lruCache.getAll(); } @Override public String toString() { Set set = Collections.synchronizedSet(getAll()); StringBuffer sb = new StringBuffer(); Iterator it = set.iterator(); while (it.hasNext()) { Map.Entry entry = (Map.Entry) it.next(); sb.append("key == " + entry.getKey()); sb.append(" value == " + entry.getValue()); sb.append("\n"); } return sb.toString(); } }
测试:
package com.javaeye.xiaobian.jgroups; public class Test { /** * @param args * @throws Exception */ public static void main(String[] args) throws Exception { // TODO Auto-generated method stub Cache cache = Cache.getInstance(); for (int i = 0; i < 10; i++) { cache.put(String.valueOf(i), "cache" + String.valueOf(i)); CacheMessage msg = new SynCacheMessage(String.valueOf(i), "cache" + String.valueOf(i), CacheConstants.CLUSTER_ENTRY_ADD); cache.getSynchronizer().sendCacheFlushMessage(msg); System.out.println(cache.size()); System.out.println(cache.toString()); Thread.currentThread().sleep(1000 * 5); } /* * Object[] keys = new Object[10]; for (int i = 0; i < 10; i++) { * keys[i] = String.valueOf(i); } CacheMessage msg1 = new * SynCacheMessage(keys, "cache", * CacheConstants.CLUSTER_ENTRY_DELETE_SOME); * * cache.getSynchronizer().sendCacheFlushMessage(msg1); */ for (int i = 0; i < 10; i++) { CacheMessage msg = new SynCacheMessage(String.valueOf(i), "cacheUpdate" + String.valueOf(i), CacheConstants.CLUSTER_ENTRY_UPDATE); cache.update(String.valueOf(i), "cacheUpdate" + String.valueOf(i)); cache.getSynchronizer().sendCacheFlushMessage(msg); System.out.println(cache.size()); System.out.println(cache.toString()); Thread.currentThread().sleep(1000 * 5); } } }
参考:
http://www.blogjava.net/swingboat/archive/2007/07/16/130565.html
http://bbs.81tech.com/read.php?tid=84461