最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

Java設(shè)計(jì)實(shí)現(xiàn)一個(gè)針對(duì)各種類型的緩存

 更新時(shí)間:2023年11月16日 10:51:08   作者:代碼哲學(xué)  
這篇文章主要為大家詳細(xì)介紹了Java如何設(shè)計(jì)實(shí)現(xiàn)一個(gè)針對(duì)各種類型的緩存,文中的示例代碼講解詳細(xì),具有一定的學(xué)習(xí)價(jià)值,感興趣的小伙伴可以了解一下

1. 設(shè)計(jì)頂層接口

// 定義為一個(gè)泛型接口,提供給抽象類使用
public interface CacheManager<T> {
    // 獲取所有的緩存item
    List<T> getAll();
    // 根據(jù)條件獲取某些緩存item
    List<T> get(Predicate<T> predicate);
    // 設(shè)置緩存
    boolean set(T t);
    // 設(shè)置緩存list
    boolean set(List<T> tList);
}

有接口必定有實(shí)現(xiàn)類或者抽象類,實(shí)現(xiàn)接口。

那為了更好地控制子類的行為,可以做一個(gè)抽象類,控制子類行為。

分析:

  • 抽象類作為緩存管理的話,那么就需要提供安全訪問(wèn)數(shù)據(jù)
  • 需要考慮線程安全問(wèn)題。
  • 花絮: 不僅要滿足上述需求,而且讓代碼盡量簡(jiǎn)潔。

2. 設(shè)計(jì)抽象類 – AbstractCacheManager

屬性設(shè)計(jì):

  • 需要一個(gè)緩存
  • 需要一個(gè)線程安全機(jī)制方案

行為設(shè)計(jì):

自己的行為:

  • 利用線程安全機(jī)制控制緩存的讀寫。
  • 權(quán)限:僅自己可訪問(wèn)

后代的行為:

  • 訪問(wèn)一些簡(jiǎn)單api方法即可實(shí)現(xiàn)安全訪問(wèn)緩存
  • 權(quán)限:公共訪問(wèn)

設(shè)計(jì)模式:

包裹思想,將后代行為方法中,包裹一層安全訪問(wèn)的行為。

Java Code:

 // properties design:
protected ConcurrentMap<String, T> cache;

private ReentrantReadWriteLock lock = new ReentrantReadWriteLock();

// subclass to implements these abstract methods.

protected abstract List<T> getAllByCache();

protected abstract void setByCache(T t);

protected abstract void setByCache(List<T> tList);

protected abstract List<T> getByCache(Predicate<T> predicate);

// next content needs to consider safety of multithreads. following methods do implements.
// entry to use
@Override
public final List<T> getAll() {
   return this.readLockThenGet(() -> this.getAllByCache());
}

@Override
public final List<T> get(Predicate<T> predicate) {
   return this.readLockThenGet(pre -> getByCache(pre), predicate);
}

@Override
public final boolean set(T t) {
   return this.writeLockThenSet((Consumer<T>) obj -> set(obj), t);
}

@Override
public final boolean set(List<T> tList) {
   return this.writeLockThenSet((Consumer<List<T>>) list -> set(list), tList);
}

// current abstract class access cache object.
private boolean writeLockThenSet(Consumer consumer, Object object){
    boolean wLock = false;
    try {
        if (!(wLock = lock.writeLock().tryLock(100, TimeUnit.MICROSECONDS))) {
            return false;
        }
        consumer.accept(object);
        return true;
    } catch (Exception e) {
        return false;
    } finally {
        if(wLock) {
            lock.writeLock().unlock();
        }
    }
}

private List<T> readLockThenGet(Supplier<List<T>> supplier){
    boolean rLock = false;
    try{
        if(!(rLock = lock.readLock().tryLock(100, TimeUnit.MICROSECONDS))){
            return null;
        }
        return supplier.get();
    }catch (Exception e){
        return null;
    }finally {
        if(rLock) {
            lock.readLock().unlock();
        }
    }
}

private List<T> readLockThenGet(Function<Predicate<T>, List<T>> function, Predicate<T> predicate){
    boolean rLock = false;
    try{
        if(!(rLock = lock.readLock().tryLock(100, TimeUnit.MICROSECONDS))){
            return null;
        }
        return function.apply(predicate);
    }catch (Exception e){
        return null;
    }finally {
        if(rLock) {
            lock.readLock().unlock();
        }
    }
}

3. 具體子類

3.1 – AlertRuleItemExpCacheManager

@Component("alertRuleItemExpCacheManager")
public class AlertRuleItemExpCacheManager<T extends AlertRuleItemExpCache> extends AbstractCacheManager<AlertRuleItemExpCache> {
   @Resource
   private AlertRuleItemExpDao alertRuleItemExpDao;

   @Override
   protected List<AlertRuleItemExpCache> getAllByCache() {
       if (null == cache) {
           List<AlertRuleItemExp> alertRuleItemSrcList =
                   alertRuleItemExpDao.selectList(Wrappers.<AlertRuleItemExp>lambdaQuery().eq(AlertRuleItemExp::getDeleted, 0));
           cache = alertRuleItemSrcList.stream().map(entity -> entity.toCache())
                   .collect(Collectors.toConcurrentMap(cache -> cache.getId().toString(), cache -> cache));
       }
       return cache.values().stream()
               .sorted(Comparator.comparing(AlertRuleItemExpCache::getId))
               .collect(Collectors.toList());
   }

   @Override
   protected void setByCache(AlertRuleItemExpCache alertRuleItemExpCache) {
       cache.put(alertRuleItemExpCache.getId().toString(), alertRuleItemExpCache);
   }

   @Override
   protected void setByCache(List<AlertRuleItemExpCache> alertRuleItemExpCacheList) {
       alertRuleItemExpCacheList.parallelStream().forEach(alertRuleItemExpCache ->
               cache.put(alertRuleItemExpCache.getId().toString(), alertRuleItemExpCache));
   }

   @Override
   protected List<AlertRuleItemExpCache> getByCache(Predicate<AlertRuleItemExpCache> predicate) {
       return getAllByCache().stream().filter(cache -> predicate.test(cache)).collect(Collectors.toList());
   }
}

3.2 – AlertRuleItemSrcCacheManager

@Component("alertRuleItemSrcCacheManager")
public class AlertRuleItemSrcCacheManager<T extends AlertRuleItemSrcCache> extends AbstractCacheManager<AlertRuleItemSrcCache> {
   @Resource
   private AlertRuleItemSrcDao alertRuleItemSrcDao;

   @Override
   protected List<AlertRuleItemSrcCache> getAllByCache() {
       if (null == cache) {
           List<AlertRuleItemSrc> alertRuleItemSrcList =
                   alertRuleItemSrcDao.selectList(Wrappers.<AlertRuleItemSrc>lambdaQuery().eq(AlertRuleItemSrc::getDeleted, 0));
           cache = alertRuleItemSrcList.stream().map(entity -> entity.toCache())
                   .collect(Collectors.toConcurrentMap(cache -> cache.getId().toString(), cache -> cache));
       }
       return cache.values().stream()
               .sorted(Comparator.comparing(AlertRuleItemSrcCache::getId))
               .collect(Collectors.toList());
   }

   @Override
   protected void setByCache(AlertRuleItemSrcCache alertRuleItemSrcCache) {
       cache.put(alertRuleItemSrcCache.getId().toString(), alertRuleItemSrcCache);
   }

   @Override
   protected void setByCache(List<AlertRuleItemSrcCache> alertRuleItemSrcCacheList) {
       alertRuleItemSrcCacheList.parallelStream().forEach(alertRuleItemSrcCache ->
               cache.put(alertRuleItemSrcCache.getId().toString(), alertRuleItemSrcCache));
   }

   @Override
   protected List<AlertRuleItemSrcCache> getByCache(Predicate<AlertRuleItemSrcCache> predicate) {
       return getAllByCache().stream().filter(cache -> predicate.test(cache)).collect(Collectors.toList());
   }
}

4. 類圖關(guān)系

以上就是Java設(shè)計(jì)實(shí)現(xiàn)一個(gè)針對(duì)各種類型的緩存的詳細(xì)內(nèi)容,更多關(guān)于Java緩存的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!

相關(guān)文章

  • springboot啟動(dòng)加載CommandLineRunner @PostConstruct問(wèn)題

    springboot啟動(dòng)加載CommandLineRunner @PostConstruct問(wèn)題

    這篇文章主要介紹了springboot啟動(dòng)加載CommandLineRunner @PostConstruct問(wèn)題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2024-08-08
  • 高并發(fā)下restTemplate的錯(cuò)誤分析方式

    高并發(fā)下restTemplate的錯(cuò)誤分析方式

    這篇文章主要介紹了高并發(fā)下restTemplate的錯(cuò)誤分析方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2021-10-10
  • Java注解中@Component和@Bean的區(qū)別

    Java注解中@Component和@Bean的區(qū)別

    這篇文章主要介紹了@Component和@Bean的區(qū)別,在這給大家簡(jiǎn)單介紹下作用對(duì)象不同:@Component 注解作用于類,而 @Bean 注解作用于方法,具體實(shí)例代碼參考下本文
    2024-03-03
  • java實(shí)現(xiàn)最短路徑算法之Dijkstra算法

    java實(shí)現(xiàn)最短路徑算法之Dijkstra算法

    這篇文章主要介紹了java實(shí)現(xiàn)最短路徑算法之Dijkstra算法, Dijkstra算法是最短路徑算法中為人熟知的一種,是單起點(diǎn)全路徑算法,有興趣的可以了解一下
    2017-10-10
  • RestTemplate添加HTTPS證書全過(guò)程解析

    RestTemplate添加HTTPS證書全過(guò)程解析

    這篇文章主要介紹了RestTemplate添加HTTPS證書全過(guò)程,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2021-10-10
  • 關(guān)于spring?aop兩種代理混用的問(wèn)題

    關(guān)于spring?aop兩種代理混用的問(wèn)題

    這篇文章主要介紹了關(guān)于spring?aop兩種代理混用的問(wèn)題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2021-11-11
  • 基于數(shù)據(jù)庫(kù)的用戶認(rèn)證實(shí)現(xiàn)SpringBoot3整合SpringSecurity6的過(guò)程

    基于數(shù)據(jù)庫(kù)的用戶認(rèn)證實(shí)現(xiàn)SpringBoot3整合SpringSecurity6的過(guò)程

    這篇文章主要介紹了基于數(shù)據(jù)庫(kù)的用戶認(rèn)證實(shí)現(xiàn)SpringBoot3整合SpringSecurity6的過(guò)程,本文通過(guò)實(shí)例圖文并茂的形式給大家介紹的非常詳細(xì),感興趣的朋友一起看看吧
    2025-05-05
  • SpringBoot微信消息接口配置詳解

    SpringBoot微信消息接口配置詳解

    這篇文章主要介紹了SpringBoot 微信消息接口配置詳解,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2019-06-06
  • Java判斷當(dāng)前日期是周幾的方法匯總

    Java判斷當(dāng)前日期是周幾的方法匯總

    在Java編程中,我們經(jīng)常會(huì)遇到需要獲取當(dāng)前日期是周幾的需求。根據(jù)國(guó)際慣例,一周通常是從周一開(kāi)始,到周日結(jié)束,記作1至7,本文將介紹幾種常用的Java方法,讓你能夠準(zhǔn)確地判斷當(dāng)前日期是周幾,感興趣的朋友一起看看吧
    2024-03-03
  • 使用Post方式提交數(shù)據(jù)到Tomcat服務(wù)器的方法

    使用Post方式提交數(shù)據(jù)到Tomcat服務(wù)器的方法

    這篇將介紹使用Post方式提交數(shù)據(jù)到服務(wù)器,由于Post的方式和Get方式創(chuàng)建Web工程是一模一樣的,只用幾個(gè)地方的代碼不同,這篇文章主要介紹了使用Post方式提交數(shù)據(jù)到Tomcat服務(wù)器的方法,感興趣的朋友一起學(xué)習(xí)吧
    2016-04-04

最新評(píng)論

高清| 尖扎县| 大冶市| 成武县| 西城区| 锡林郭勒盟| 左贡县| 沁水县| 灌南县| 当阳市| 霞浦县| 大余县| 太原市| 腾冲县| 大石桥市| 浏阳市| 都匀市| 洛浦县| 黄大仙区| 竹北市| 隆安县| 家居| 乐东| 青川县| 阿鲁科尔沁旗| 漳平市| 万全县| 潢川县| 买车| 竹山县| 察隅县| 双桥区| 灵台县| 翼城县| 辽中县| 唐河县| 阿勒泰市| 望奎县| 宣威市| 蒙城县| 工布江达县|