Java中TimedCache緩存對象的詳細使用教程
一、TimedCache 是什么?
TimedCache是一個泛型類,它的主要作用通常是在一定時間范圍內對特定鍵值對進行緩存,并且能夠根據(jù)設定的時間策略來自動清理過期的緩存項。
TimedCache是一種帶有時間控制功能的緩存數(shù)據(jù)結構。在 Java 中,緩存是一種用于臨時存儲數(shù)據(jù)的機制,目的是為了減少重復計算或者重復的數(shù)據(jù)獲取操作,提高程序的性能。而TimedCache在此基礎上增加了時間維度的管理。
二、常見功能及使用場景
緩存存儲:可以將以String為鍵、BigDecimal為值的鍵值對存入緩存中,方便后續(xù)快速獲取,避免重復計算或查詢相同的數(shù)據(jù)。其它類型也可以。(理解為Map集合,鍵值對)
時間控制:設置緩存項的有效期,一旦超過指定時間,緩存項會被自動視為過期并可能被清理掉。這有助于保證緩存數(shù)據(jù)的時效性,例如在處理實時金融數(shù)據(jù)(如匯率、股票價格等,這里值用BigDecimal表示很合適)時,舊的數(shù)據(jù)在一定時間后就不再有價值,通過定時清理過期緩存可確保獲取到相對新的數(shù)據(jù)。
緩存獲取:通過給定的String鍵,可以快速從緩存中獲取對應的BigDecimal值,如果緩存命中則直接返回緩存中的值,提高數(shù)據(jù)訪問效率。
三、使用場景
金融數(shù)據(jù)處理:如前面提到的匯率、股票價格等數(shù)據(jù)的緩存。金融數(shù)據(jù)經(jīng)常需要實時更新,但在短時間內可能會被多次查詢,使用TimedCache<String, BigDecimal>可以緩存這些數(shù)據(jù),在有效期內直接從緩存獲取,減少對數(shù)據(jù)源(如金融數(shù)據(jù)接口)的頻繁訪問,提高系統(tǒng)響應速度。
電商價格緩存:在電商系統(tǒng)中,商品價格可能會根據(jù)促銷活動等因素實時變動,但在一定時間段內(比如促銷活動期間),對于同一商品的價格查詢較為頻繁。將商品 ID(可以用String表示)作為鍵,商品價格(用BigDecimal表示)作為值存入TimedCache,可以在活動期間有效緩存價格數(shù)據(jù),提高查詢效率。
統(tǒng)計數(shù)據(jù)緩存:例如網(wǎng)站的實時流量統(tǒng)計數(shù)據(jù),以某個統(tǒng)計指標的名稱(String)為鍵,對應的統(tǒng)計數(shù)值(可能是BigDecimal類型,如流量的具體數(shù)值等)為值進行緩存。這樣在短時間內可以快速獲取統(tǒng)計數(shù)據(jù),并且通過設置合適的時間限制,確保數(shù)據(jù)能及時更新。
四、使用
1、相關依賴
<dependency>
<groupId>cn.hutool</groupId>
<artifactId>hutool-all</artifactId>
<version>5.4.6</version>
</dependency>
<dependency>
<groupId>com.google.guava</groupId>
<artifactId>guava</artifactId>
<version>30.1.1-jre</version>
</dependency>
2、使用
2.1、自定義工具簡單使用:
private static final TimedCache<String, String> TIMED_CACHE = CacheUtil.newTimedCache(5000);
static {
/** 每5ms檢查一次過期 */
TIMED_CACHE.schedulePrune(5);
}
/**
* 存入鍵值對,提供消逝時間
*
* @param key
* @param value
* @param timeout
*/
public static void put(String key, String value, Long timeout) {
/** 設置消逝時間 */
TIMED_CACHE.put(key, value, timeout);
}
/**
* 每次重新get一次緩存,均會重新刷新消逝時間
* @param key
* @return
*/
public static String get(String key) {
return TIMED_CACHE.get(key);
}
public static void main(String[] args) {
put("haha", "1", 3000L);
ThreadUtil.sleep(2000);
// if (TIMED_CACHE.containsKey("haha")) {
// System.out.println("aa");
// }
System.out.println("第1次結果:" + get("haha"));
ThreadUtil.sleep(2000);
System.out.println("第2次結果:" + get("haha"));
ThreadUtil.sleep(5000);
System.out.println("第3次結果:" + get("haha"));
// 取消定時清理
TIMED_CACHE.cancelPruneSchedule();
}
2.2、糊涂工具使用
CacheUtil具體方法:
/**
* 緩存工具類
* @author Looly
*@since 3.0.1
*/
public class CacheUtil {
/**
* 創(chuàng)建FIFO(first in first out) 先進先出緩存.
*
* @param <K> Key類型
* @param <V> Value類型
* @param capacity 容量
* @param timeout 過期時長,單位:毫秒
* @return {@link FIFOCache}
*/
public static <K, V> FIFOCache<K, V> newFIFOCache(int capacity, long timeout){
return new FIFOCache<>(capacity, timeout);
}
/**
* 創(chuàng)建FIFO(first in first out) 先進先出緩存.
*
* @param <K> Key類型
* @param <V> Value類型
* @param capacity 容量
* @return {@link FIFOCache}
*/
public static <K, V> FIFOCache<K, V> newFIFOCache(int capacity){
return new FIFOCache<>(capacity);
}
/**
* 創(chuàng)建LFU(least frequently used) 最少使用率緩存.
*
* @param <K> Key類型
* @param <V> Value類型
* @param capacity 容量
* @param timeout 過期時長,單位:毫秒
* @return {@link LFUCache}
*/
public static <K, V> LFUCache<K, V> newLFUCache(int capacity, long timeout){
return new LFUCache<>(capacity, timeout);
}
/**
* 創(chuàng)建LFU(least frequently used) 最少使用率緩存.
*
* @param <K> Key類型
* @param <V> Value類型
* @param capacity 容量
* @return {@link LFUCache}
*/
public static <K, V> LFUCache<K, V> newLFUCache(int capacity){
return new LFUCache<>(capacity);
}
/**
* 創(chuàng)建LRU (least recently used)最近最久未使用緩存.
*
* @param <K> Key類型
* @param <V> Value類型
* @param capacity 容量
* @param timeout 過期時長,單位:毫秒
* @return {@link LRUCache}
*/
public static <K, V> LRUCache<K, V> newLRUCache(int capacity, long timeout){
return new LRUCache<>(capacity, timeout);
}
/**
* 創(chuàng)建LRU (least recently used)最近最久未使用緩存.
*
* @param <K> Key類型
* @param <V> Value類型
* @param capacity 容量
* @return {@link LRUCache}
*/
public static <K, V> LRUCache<K, V> newLRUCache(int capacity){
return new LRUCache<>(capacity);
}
/**
* 創(chuàng)建定時緩存.
*
* @param <K> Key類型
* @param <V> Value類型
* @param timeout 過期時長,單位:毫秒
* @return {@link TimedCache}
*/
public static <K, V> TimedCache<K, V> newTimedCache(long timeout){
return new TimedCache<>(timeout);
}
/**
* 創(chuàng)建弱引用緩存.
*
* @param <K> Key類型
* @param <V> Value類型
* @param timeout 過期時長,單位:毫秒
* @return {@link WeakCache}
* @since 3.0.7
*/
public static <K, V> WeakCache<K, V> newWeakCache(long timeout){
return new WeakCache<>(timeout);
}
/**
* 創(chuàng)建無緩存實現(xiàn).
*
* @param <K> Key類型
* @param <V> Value類型
* @return {@link NoCache}
*/
public static <K, V> NoCache<K, V> newNoCache(){
return new NoCache<>();
}
}
Cache接口具體方法:
/**
* 緩存接口
*
* @param <K> 鍵類型
* @param <V> 值類型
* @author Looly, jodd
*/
public interface Cache<K, V> extends Iterable<V>, Serializable {
/**
* 返回緩存容量,{@code 0}表示無大小限制
*
* @return 返回緩存容量,{@code 0}表示無大小限制
*/
int capacity();
/**
* 緩存失效時長, {@code 0} 表示沒有設置,單位毫秒
*
* @return 緩存失效時長, {@code 0} 表示沒有設置,單位毫秒
*/
long timeout();
/**
* 將對象加入到緩存,使用默認失效時長
*
* @param key 鍵
* @param object 緩存的對象
* @see Cache#put(Object, Object, long)
*/
void put(K key, V object);
/**
* 將對象加入到緩存,使用指定失效時長<br>
* 如果緩存空間滿了,{@link #prune()} 將被調用以獲得空間來存放新對象
*
* @param key 鍵
* @param object 緩存的對象
* @param timeout 失效時長,單位毫秒
*/
void put(K key, V object, long timeout);
/**
* 從緩存中獲得對象,當對象不在緩存中或已經(jīng)過期返回{@code null}
* <p>
* 調用此方法時,會檢查上次調用時間,如果與當前時間差值大于超時時間返回{@code null},否則返回值。
* <p>
* 每次調用此方法會刷新最后訪問時間,也就是說會重新計算超時時間。
*
* @param key 鍵
* @return 鍵對應的對象
* @see #get(Object, boolean)
*/
default V get(K key) {
return get(key, true);
}
/**
* 從緩存中獲得對象,當對象不在緩存中或已經(jīng)過期返回Func0回調產生的對象
* <p>
* 調用此方法時,會檢查上次調用時間,如果與當前時間差值大于超時時間返回{@code null},否則返回值。
* <p>
* 每次調用此方法會刷新最后訪問時間,也就是說會重新計算超時時間。
*
* @param key 鍵
* @param supplier 如果不存在回調方法,用于生產值對象
* @return 值對象
*/
default V get(K key, Func0<V> supplier) {
return get(key, true, supplier);
}
/**
* 從緩存中獲得對象,當對象不在緩存中或已經(jīng)過期返回Func0回調產生的對象
* <p>
* 調用此方法時,會檢查上次調用時間,如果與當前時間差值大于超時時間返回{@code null},否則返回值。
* <p>
* 每次調用此方法會可選是否刷新最后訪問時間,{@code true}表示會重新計算超時時間。
*
* @param key 鍵
* @param isUpdateLastAccess 是否更新最后訪問時間,即重新計算超時時間。
* @param supplier 如果不存在回調方法,用于生產值對象
* @return 值對象
*/
V get(K key, boolean isUpdateLastAccess, Func0<V> supplier);
/**
* 從緩存中獲得對象,當對象不在緩存中或已經(jīng)過期返回{@code null}
* <p>
* 調用此方法時,會檢查上次調用時間,如果與當前時間差值大于超時時間返回{@code null},否則返回值。
* <p>
* 每次調用此方法會可選是否刷新最后訪問時間,{@code true}表示會重新計算超時時間。
*
* @param key 鍵
* @param isUpdateLastAccess 是否更新最后訪問時間,即重新計算超時時間。
* @return 鍵對應的對象
*/
V get(K key, boolean isUpdateLastAccess);
/**
* 返回包含鍵和值得迭代器
*
* @return 緩存對象迭代器
* @since 4.0.10
*/
Iterator<CacheObj<K, V>> cacheObjIterator();
/**
* 從緩存中清理過期對象,清理策略取決于具體實現(xiàn)
*
* @return 清理的緩存對象個數(shù)
*/
int prune();
/**
* 緩存是否已滿,僅用于有空間限制的緩存對象
*
* @return 緩存是否已滿,僅用于有空間限制的緩存對象
*/
boolean isFull();
/**
* 從緩存中移除對象
*
* @param key 鍵
*/
void remove(K key);
/**
* 清空緩存
*/
void clear();
/**
* 緩存的對象數(shù)量
*
* @return 緩存的對象數(shù)量
*/
int size();
/**
* 緩存是否為空
*
* @return 緩存是否為空
*/
boolean isEmpty();
/**
* 是否包含key
*
* @param key KEY
* @return 是否包含key
*/
boolean containsKey(K key);
/**
* 設置監(jiān)聽
*
* @param listener 監(jiān)聽
* @return this
* @since 5.5.2
*/
default Cache<K, V> setListener(CacheListener<K, V> listener){
return this;
}
}
使用:創(chuàng)建一個緩存對象,自動清理時間單位為毫秒,自動清理時間為3秒鐘
public static void main(String[] args) {
TimedCache<String, BigDecimal> dataCache = CacheUtil.newTimedCache(3000);
String k = "key";
BigDecimal v = new BigDecimal("100");
dataCache.put(k,v);
System.out.println("第1次結果:" + dataCache.get(k));
ThreadUtil.sleep(2000);
System.out.println("第2次結果:" + dataCache.get(k));
ThreadUtil.sleep(5000);
System.out.println("第3次結果:" + dataCache.get(k));
System.out.println("第3次結果-get方法:" + dataCache.get(k, () -> v)); //使用此方法,如果為空值就把數(shù)據(jù)重新賦值并且返回
System.out.println("第4次結果:" + dataCache.get(k));
}

以上就是Java中TimedCache緩存對象的詳細使用教程的詳細內容,更多關于Java TimedCache使用的資料請關注腳本之家其它相關文章!
相關文章
ReentrantLock 非公平鎖實現(xiàn)原理詳解
這篇文章主要為大家介紹了ReentrantLock 非公平鎖實現(xiàn)原理詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪2022-12-12
Spring\SpringBoot配置連接數(shù)據(jù)庫的方法
最近在學習SpringBoot,第一步就是要配置數(shù)據(jù)庫,本文詳細的介紹了Spring\SpringBoot配置連接數(shù)據(jù)庫的方法,有需要的朋友們下面隨著小編來一起學習學習吧2021-06-06
JavaWeb response和request對象原理及實例解析
這篇文章主要介紹了JavaWeb response和request對象原理及實例解析,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友可以參考下2020-11-11
從零開始讓你的Spring?Boot項目跑在Linux服務器
這篇文章主要給大家介紹了如何從零開始讓你的Spring?Boot項目跑在Linux服務器的相關資料,由于springboot是內嵌了tomcat,所以可以直接將項目打包上傳至服務器上,需要的朋友可以參考下2021-11-11
SpringMVC+Mybatis實現(xiàn)的Mysql分頁數(shù)據(jù)查詢的示例
本篇文章主要介紹了SpringMVC+Mybatis實現(xiàn)的Mysql分頁數(shù)據(jù)查詢的示例,具有一定的參考價值,有興趣的可以了解一下2017-08-08
spring實現(xiàn)bean對象創(chuàng)建代碼詳解
這篇文章主要介紹了spring實現(xiàn)bean對象創(chuàng)建代碼詳解,具有一定借鑒價值,需要的朋友可以參考下2017-12-12

