網站首頁 編程語言 正文
一、什么是緩存擊穿
當一個key是熱點key時,一般會做緩存來抗大量并發,但當緩存失效的一瞬間,這些大量的并發請求會擊穿緩存,直接請求數據庫
為了避免緩存擊穿,一種解決方法可以設置緩存永不過期,另一種可以使用golang的包 singleflight golang.org/x/sync/singleflight
二、原理
多個并發請求對一個失效key進行數據獲取時,只會有其中一個去直接獲取數據,其它請求會阻塞等待第一個請求返回給它們結果
三、實現
package singleflight import ( "sync" ) var WaitCount int var DirectCount int type Caller struct { val interface{} err error wg sync.WaitGroup } type Group struct { mu sync.RWMutex m map[string]*Caller } func (g *Group) Do(key string, fn func() (interface{}, error)) (interface{}, error) { g.mu.Lock() if g.m == nil { g.m = make(map[string]*Caller) } c, ok := g.m[key] if ok { //阻塞等待其它已經執行此操作的返回結果 g.mu.Unlock() c.wg.Wait() WaitCount++ return c.val, c.err } //直接請求獲取數據 c = &Caller{} g.m[key] = c c.wg.Add(1) g.mu.Unlock() c.val, c.err = fn() c.wg.Done() g.mu.Lock() delete(g.m, key) g.mu.Unlock() DirectCount++ return c.val, c.err }
測試:
func TestGroup_Do(t *testing.T) { sg := &Group{} wg := sync.WaitGroup{} for i := 0; i < 10000; i++ { fn := func() (interface{}, error) { return i, nil } wg.Add(1) go func() { defer wg.Done() got, err := sg.Do("test-key", fn) _, _ = got, err //t.Log("got:", i) }() } wg.Wait() fmt.Println("waitCount:", WaitCount) fmt.Println("DirectCount:", DirectCount) }
輸出:
waitCount: 8323
DirectCount: 1401
原文鏈接:https://juejin.cn/post/7012936620177358879
相關推薦
- 2022-07-06 C#中LINQ?to?DataSet操作及DataTable與LINQ相互轉換_C#教程
- 2022-07-16 Linux中啟動Docker容器報錯:Error response from daemon: dri
- 2021-12-09 golang中gin框架接入jwt使用token驗證身份_Golang
- 2023-02-01 Bat腳本之在文件中查找多個字符串并保存到文件中_DOS/BAT
- 2023-11-12 Check failed: top_shape[j] == bottom[i]->shape(j)
- 2022-12-21 Python實現簡易計算器的示例代碼_python
- 2022-07-26 Android自定義評分控件的完整實例_Android
- 2022-05-18 TypeScript中的接口和泛型你了解嗎_基礎知識
- 最近更新
-
- window11 系統安裝 yarn
- 超詳細win安裝深度學習環境2025年最新版(
- Linux 中運行的top命令 怎么退出?
- MySQL 中decimal 的用法? 存儲小
- get 、set 、toString 方法的使
- @Resource和 @Autowired注解
- Java基礎操作-- 運算符,流程控制 Flo
- 1. Int 和Integer 的區別,Jav
- spring @retryable不生效的一種
- Spring Security之認證信息的處理
- Spring Security之認證過濾器
- Spring Security概述快速入門
- Spring Security之配置體系
- 【SpringBoot】SpringCache
- Spring Security之基于方法配置權
- redisson分布式鎖中waittime的設
- maven:解決release錯誤:Artif
- restTemplate使用總結
- Spring Security之安全異常處理
- MybatisPlus優雅實現加密?
- Spring ioc容器與Bean的生命周期。
- 【探索SpringCloud】服務發現-Nac
- Spring Security之基于HttpR
- Redis 底層數據結構-簡單動態字符串(SD
- arthas操作spring被代理目標對象命令
- Spring中的單例模式應用詳解
- 聊聊消息隊列,發送消息的4種方式
- bootspring第三方資源配置管理
- GIT同步修改后的遠程分支