MapMaker做爲大多數基本緩存功能地提供者。java
ConcurrentMap<String,Book> books = new MapMaker().concurrencyLevel(2) //併發級別,即容許最多2個線程併發更新, 默認值爲4 .softValues() //使用SoftReference引用對象包裝value .makeMap(); //構建Map對象
Cache類:緩存
基本操做併發
put(key,value); //存放key-value V value = cache.get(key, Callable<? Extends V> value); //獲取key對應的緩存對象,不存在或調用Callable實例的call方法來返回key對應的值
上面的cache.get有效代替了咱們一般的操做:異步
value = cache.get(key); if(value == null){ value = someService.retrieveValue(); cache.put(key,value); }
上面經過Callable獲取值是一個異步過程,咱們也能夠經過非異步來獲取值:async
cache.get(key,Callables.returning(someService.retrieveValue()); //同步方式獲取不存在的key緩存
一樣咱們也能夠使緩存的數據失效:ide
invalidate(key) //廢棄key對應的緩存 invalidateAll() //廢棄全部的緩存 invalidateAll(Iterable<?> keys) //廢棄keys對應的緩存
LoadingCache是Cache的擴展類,具備自加載功能。ui
基本操做。spa
Book book = loadingCache.get(id); //獲取key爲id的緩存 ImmutableMap<key,value> map = cache.getAll(Iterable<? Extends key>); //獲取多個key的緩存,並返回不可變map對象 refresh(key); //刷新key對應的緩存
CacheBuilder經過構建器模式構建Cache和LoadingCache實例。線程
構建LoadingCache對象實例一。code
LoadingCache<String, TradeAccount> traLoadingCache = CacheBuilder.newBuilder() .expireAfterAccess(5L, TimeUnit.MINUTES) //5分鐘後緩存失效 .maximumSize(5000L) //最大緩存5000個對象 .removalListener(new TradeAccountRemovalListener()) //註冊緩存對象移除監聽器 .ticker(Ticker.systemTicker()) //定義緩存對象失效的時間精度爲納秒級 .build(new CacheLoader<String, TradeAccount>(){ @Override public TradeAccount load(String key) throws Exception { // load a new TradeAccount not exists in cache return null; } });
經過SoftReference對象實現自動回收
LoadingCache<String, TradeAccount> traLoadingCache = CacheBuilder.newBuilder() .expireAfterAccess(5L, TimeUnit.MINUTES) //5分鐘後緩存失效 .softValues() //使用SoftReference對象封裝value, 使得內存不足時,自動回收 .removalListener(new TradeAccountRemovalListener()) //註冊緩存對象移除監聽器 .ticker(Ticker.systemTicker()) //定義緩存對象失效的時間精度爲納秒級 .build(new CacheLoader<String, TradeAccount>(){ @Override public TradeAccount load(String key) throws Exception { // load a new TradeAccount not exists in cache return null; } });
構建一個可自動刷新緩存的LoadingCache
LoadingCache<String, TradeAccount> traLoadingCache = CacheBuilder.newBuilder() .concurrencyLevel(10) //容許同時最多10個線程併發修改 .refreshAfterWrite(5L, TimeUnit.SECONDS) //5秒中後自動刷新 .removalListener(new TradeAccountRemovalListener()) //註冊緩存對象移除監聽器 .ticker(Ticker.systemTicker()) //定義緩存對象失效的時間精度爲納秒級 .build(new CacheLoader<String, TradeAccount>(){ @Override public TradeAccount load(String key) throws Exception { // load a new TradeAccount not exists in cache return null; } });
CacheBuilderSpec能夠用於構建CacheBuilder時的配置描述。
String configString = "concurrencyLevel=10,refreshAfterWrite=5s"
經過CacheBuilderSpec構建LoadingCache:
String spec = "concurrencyLevel=10,expireAfterAccess=5m,softValues"; CacheBuilderSpec cacheBuilderSpec = CacheBuilderSpec.parse(spec); CacheBuilder<Object, Object> cacheBuilder = CacheBuilder.from(cacheBuilderSpec); LoadingCache<String, TradeAccount> traLoadingCache = cacheBuilder .ticker(Ticker.systemTicker()) .removalListener(new TradeAccountRemovalListener()) .build(new CacheLoader<String, TradeAccount>(){ @Override public TradeAccount load(String key) throws Exception { // load a new TradeAccount not exists in cache return null; } });
構建CacheLoader
//用Function構建CacheLoader, 將輸入轉換成輸出 CacheLoader<Key,value> cacheLoader = CacheLoader.from(Function<Key,Value> func); //經過Supplier構建CacheLoader CacheLoader<Object,Value> cacheLoader = CacheLoader.from(Supplier<Value> supplier);
用於收集一些緩存信息。
LoadingCache<String,TradeAccount> tradeAccountCache = CacheBuilder.newBuilder().recordStats() //開啓記錄狀態
獲取CacheStat對象
CacheStats cacheStats = cache.stats();
經過CacheStat能夠獲取的信息
1.加載新值消耗的平均時間 2.命中次數 3.未命中次數 ...
用於監聽Cache中的key被移除時。
用於接收觸發RemovalListener的onRemoval的參數傳入,可獲取對應key,value等。
經過RemovalNotification.getCause()還能夠知道該對象被移除的緣由.
public enum RemovalCause { //用戶手動移除 EXPLICIT, //用戶手動替換 REPLACED, //被垃圾回收 COLLECTED, //超時過時 EXPIRED, //因爲緩存大小限制 SIZE; }
咱們能夠異步執行RemovalListener的onRemoval觸發動做
RemovalListener<String,TradeAccount> myRemovalListener = new RemovalListener<String, TradeAccount>() { @Override public void onRemoval(RemovalNotification<String,TradeAccount> notification) { //Do something here } }; RemovalListener<String,TradeAccount> removalListener = RemovalListeners.asynchronous(myRemovalListener,executorService);
上面的步驟必須在咱們註冊RemovalListener到 CacheBuilder以前。