Mat*_*all 13 java caching hadoop berkeley-db ehcache
关注这个问题,似乎基于文件或磁盘的Map
实现可能是我在那里提到的问题的正确解决方案.精简版:
Map
实现了一个ConcurrentHashMap
.在工作中,(强烈)建议我使用SQLite解决这个问题,但在询问上一个问题之后,我认为数据库不是这项工作的正确工具.所以 - 让我知道这听起来有多疯狂 - 我认为更好的解决方案是Map
存储在磁盘上.
不好的主意:自己实现这个.更好的主意:使用别人的图书馆!哪一个?
n
几天前的条目.如果我必须手动执行此操作,这不是什么大问题.new ConcurrentHashMap<Foo, Bar>();
到new SomeDiskStoredMap<Foo, Bar>();
(no inserts for an hour)
这样(insert 10,000 objects at once)
.Ehcache和Berkeley DB现在看起来都很合理.任何方向的任何特定建议?
更新(首次发布后约4年......):请注意,在较新版本的ehcache中,缓存项的持久性仅在付费产品中可用.谢谢@boday指出这一点.
ehcache很棒.它将为您提供在内存,磁盘或内存中实现映射以及溢出到磁盘所需的灵活性.如果你使用这个非常简单的java.util.Map包装器,那么使用它非常简单:
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.Set;
import net.sf.ehcache.Cache;
import net.sf.ehcache.Element;
import org.apache.log4j.Logger;
import com.google.common.collect.Sets;
public class EhCacheMapAdapter<K,V> implements Map<K,V> {
@SuppressWarnings("unused")
private final static Logger logger = Logger
.getLogger(EhCacheMapAdapter.class);
public Cache ehCache;
public EhCacheMapAdapter(Cache ehCache) {
super();
this.ehCache = ehCache;
} // end constructor
@Override
public void clear() {
ehCache.removeAll();
} // end method
@Override
public boolean containsKey(Object key) {
return ehCache.isKeyInCache(key);
} // end method
@Override
public boolean containsValue(Object value) {
return ehCache.isValueInCache(value);
} // end method
@Override
public Set<Entry<K, V>> entrySet() {
throw new UnsupportedOperationException();
} // end method
@SuppressWarnings("unchecked")
@Override
public V get(Object key) {
if( key == null ) return null;
Element element = ehCache.get(key);
if( element == null ) return null;
return (V)element.getObjectValue();
} // end method
@Override
public boolean isEmpty() {
return ehCache.getSize() == 0;
} // end method
@SuppressWarnings("unchecked")
@Override
public Set<K> keySet() {
List<K> l = ehCache.getKeys();
return Sets.newHashSet(l);
} // end method
@SuppressWarnings("unchecked")
@Override
public V put(K key, V value) {
Object o = this.get(key);
if( o != null ) return (V)o;
Element e = new Element(key,value);
ehCache.put(e);
return null;
} // end method
@Override
public V remove(Object key) {
V retObj = null;
if( this.containsKey(key) ) {
retObj = this.get(key);
} // end if
ehCache.remove(key);
return retObj;
} // end method
@Override
public int size() {
return ehCache.getSize();
} // end method
@Override
public Collection<V> values() {
throw new UnsupportedOperationException();
} // end method
@Override
public void putAll(Map<? extends K, ? extends V> m) {
for( K key : m.keySet() ) {
this.put(key, m.get(key));
} // end for
} // end method
} // end class
Run Code Online (Sandbox Code Playgroud)
你有没有听说过流行框架?
编辑对该术语的一些澄清.
就像James Gosling现在所说的那样,没有SQL DB像内存存储一样高效.流行框架(最常见的是prevayler和space4j)建立在内存上,可能存储在磁盘上的存储上.他们是如何工作的?事实上,它看似简单:存储对象包含所有持久性实体.此存储只能通过可序列化操作进行更改.因此,将对象放入存储器是在隔离的上下文中执行的Put操作.由于此操作是可序列化的,因此它可以(取决于配置)也保存在磁盘上以实现长期持久性.然而,主数据存储库是存储器,其以高内存使用为代价提供了无疑的快速访问时间.
另一个优点是,由于它们非常简单,这些框架几乎不包含十分之一的类
考虑到你的问题,我立即想到了Space4J的使用(因为它提供了对很少使用的对象的"钝化"的支持,也就是说它们的索引键在内存中,但是只要它们是对象就保存在磁盘上不曾用过).
请注意,您还可以在c2wiki上找到一些信息.
归档时间: |
|
查看次数: |
3281 次 |
最近记录: |