自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

騰訊面試之言淺意深 Redis

存儲 存儲軟件 Redis
字符串 String、列表 list、集合 set、有序集合 sortedSet、哈希 hash、位圖 bitMap 、Stream 流(redis 5.0 版本新特性)、HyperLogLog。

[[398188]]

本文轉(zhuǎn)載自微信公眾號「碼農(nóng)私房話」,作者Liew。轉(zhuǎn)載本文請聯(lián)系碼農(nóng)私房話公眾號。

redis 與 memcached 的區(qū)別

數(shù)據(jù)類型:memcached 只支持 string,而 redis 還支持列表 list、集合 set、hash、有序集合 sortedSet、位圖 bitMap、HyperLogLog 以及 Stream(redis 5.0 版本新特性)。

主從備份:redis 支持主從的模式應用,主數(shù)據(jù)庫有多個副本,使得可以擴展數(shù)據(jù)庫讀取能力,且具有高可用性。

數(shù)據(jù)存儲:memcached 與 redis 都支持數(shù)據(jù)存儲在內(nèi)存中,除此之外, redis 還支持將數(shù)據(jù)保存在磁盤中。

持久化:memcached 的數(shù)據(jù)只保存在內(nèi)存,宕機后數(shù)據(jù)將丟失,而 redis 可利用持久化機制將數(shù)據(jù)保留在磁盤上,用于歸檔或恢復。

事務:redis 支持事務,可將一組命令原子操作地執(zhí)行。

發(fā)布/訂閱:redis 支持具有模式匹配的發(fā)布/訂閱消息功能。

Lua 腳本:redis 允許執(zhí)行事務性 Lua 腳本,幫助提高性能并簡化應用代碼。

地理空間支持:redis 具有專用命令,可以處理大規(guī)模實時地理空間數(shù)據(jù),例如查找兩個元素(人或地方)之間的距離以及查找點的給定距離內(nèi)的所有元素。

線程模型:redis 使用的是單線程模型,而 memcached 使用的是多線程架構(gòu),可以利用多個核心及擴大計算能力來處理更多操作,在一定程度上性能會比 redis 優(yōu)秀。

多語言客戶端支持:redis 和 memcached 都支持多種語言客戶端,包括 Java、Python、Php、C、C ++、Go等。

redis 有哪些數(shù)據(jù)類型

字符串 String、列表 list、集合 set、有序集合 sortedSet、哈希 hash、位圖 bitMap 、Stream 流(redis 5.0 版本新特性)、HyperLogLog。

redis 的使用場景有哪些?

熱點數(shù)據(jù)緩存:對于系統(tǒng)中常用且不常更新的數(shù)據(jù)可加載到 redis ,提升性能。

分布式鎖:結(jié)合 setexnx命令實現(xiàn)或者直接用 Redisson 的功能。

排行榜:使用 Sorted Sets 輕松實現(xiàn)游戲排行榜。

隊列:redis 的 list 底層是鏈表,但同時也可用于隊列,使用 lpush 、brpop 命令操作隊列。

計數(shù)器:控制一個手機號一天限制發(fā)送 5 條短信,或用于庫存扣減,保證不超發(fā)。

布隆過濾器:快速準確判斷 10 萬個號碼是否在 10 億個號碼庫里或者請求 IP 地址是否在 10 億 的黑名單庫。

GeoHash:實現(xiàn)美團外賣或餓了么「附近的商家」功能,或者計算兩個人之間的距離。

BitMap:使用位圖可實現(xiàn)用戶類似近 7 天簽到功能或某時間范圍內(nèi)用戶的登錄狀態(tài)。

延遲操作:使用 SortSet 實現(xiàn)延遲隊列,例如訂單在 30 分鐘內(nèi)未支付則自動取消并發(fā)送短信。

好友關(guān)系及點贊:set 集合可用于記錄文章的點贊、閱讀數(shù);用 zinterstore 查詢共同好友、zset 實現(xiàn)好友關(guān)系。

分布式限流:基于令牌桶算法,利用 Lua 腳本實現(xiàn)分布式限流,Spring Cloud Gateway中的限流就是典型例子。

redis 線程模型

在 redis 6 版本前均采用的是單線程模型,基于 Reactor 模式開發(fā)了網(wǎng)絡事件處理器,redis 在處理客戶端的請求時,包括請求命令的獲取、解析、執(zhí)行、內(nèi)容返回等都由一個順序串行的主線程處理,這就是所謂的“單線程”。

但在 redis 6 版本后便正式引入多線程模型,隨著越來越復雜的業(yè)務場景,需要更高的 QPS,常用的解決方案是對數(shù)據(jù)分區(qū)并采用更多的服務器,但該方案缺點是 投入的成本高,維護的 redis 服務器多。

在redis 執(zhí)行期間,網(wǎng)絡的讀寫及系統(tǒng)調(diào)用占用了大部分 CPU 時間,而瓶頸主要在于網(wǎng)絡的 IO 消耗,因此優(yōu)化的主要有以下原因:

  • 充分利用服務器 CPU 資源,而目前 redis 主線程只能利用一個核。
  • 多線程任務可以分攤 redis 同步 IO 讀寫負荷,例如:memcached。

redis 為何選擇單線程網(wǎng)絡模型?

  • 使用單線程模型能帶來更好的可維護性,方便開發(fā)與調(diào)試。
  • 使用單線程模型也能并發(fā)的處理客戶端的請求。
  • 避免頻繁的 CPU 上下文切換開銷及多線程帶來的安全同步。
  • redis 服務中運行的絕大多數(shù)操作的性能瓶頸都不是 CPU。

從官方中給出的解析可以看到官方認為 redis 的大多數(shù)命令操作性能瓶頸并不在 CPU,主要受限于內(nèi)存和網(wǎng)絡。

  • It’s not very frequent that CPU becomes your bottleneck with Redis, as usually Redis is either memory or network bound. For instance, using pipelining Redis running on an average Linux system can deliver even 1 million requests per second, so if your application mainly uses O(N) or O(log(N)) commands, it is hardly going to use too much CPU.

因此,第三點起到?jīng)Q定性的因素,另外兩點是使用單線程帶來的好處。

redis 為什么這么”快“?

1、完全基于內(nèi)存,絕大部分請求是純粹的內(nèi)存操作。

2、采用單線程,避免了不必要的上下文切換和競爭條件,但同時也無法利用多核的優(yōu)勢。

3、使用多路 I/O 復用模型,實現(xiàn)高吞吐的 IO 操作。

4、數(shù)據(jù)結(jié)構(gòu)簡單,大多數(shù)讀/寫操作為 O(n) 或 O(log(N))。

使用 redis 的隊列存在什么問題 ?

1、存在消息丟失的可能性。

2、生產(chǎn)速度與消費速度不匹配引起消息堆積,將會導致 redis 內(nèi)存耗盡。

3、隊列中的消息不允許重復消費。

redis 如何實現(xiàn)分布式鎖 ?

實現(xiàn)思想大致如下:

1、使用 setnx、setex 命令把當前獲取鎖的請求信息(鎖的 key、線程 id等)保存到 redis,同時記錄同個線程獲取鎖的次數(shù)(實現(xiàn)可重入功能)。

2、釋放瑣時,為避免誤刪,需判斷當前操作的線程是否與加鎖的是同一個,若是同一個則 del 對應鎖的 key 即可。

涉及到多個命令執(zhí)行,需把獲取鎖、釋放鎖的邏輯放在 lua 腳本中保證原子性,具體可參考 Redisson 分布式鎖的實現(xiàn):

獲取鎖邏輯代碼:

  1. if (redis.call('exists', KEYS[1]) == 0) then  
  2.   redis.call('hset', KEYS[1], ARGV[2], 1);  
  3.   redis.call('pexpire', KEYS[1], ARGV[1]);  
  4.   return nil;  
  5. end
  6.  
  7. if (redis.call('hexists', KEYS[1], ARGV[2]) == 1) then 
  8.   redis.call('hincrby', KEYS[1], ARGV[2], 1); 
  9.   redis.call('pexpire', KEYS[1], ARGV[1]); 
  10.   return nil; 
  11. end
  12.  
  13. return redis.call('pttl', KEYS[1]); 

釋放鎖邏輯代碼:

  1. if (redis.call('hexists', KEYS[1], ARGV[3]) == 0) then 
  2.   return nil; 
  3. end
  4. local counter = redis.call('hincrby', KEYS[1], ARGV[3], -1);  
  5. if (counter > 0) then  
  6.   redis.call('pexpire', KEYS[1], ARGV[2]);  
  7.   return 0;  
  8. else 
  9.   redis.call('del', KEYS[1]);  
  10.   redis.call('publish', KEYS[2], ARGV[1]);  
  11.   return 1;  
  12. end
  13. return nil; 

如何解決業(yè)務端未執(zhí)行完邏輯,但鎖已過期?

可參考 Redisson 框架處理鎖租期的方案,在每次獲取鎖時判斷 leaseTime 是否為 -1 ,若是則在獲取鎖成功后新建一個線程專門檢測對應鎖的 key 是否過期,過期的話則調(diào)用 lua 腳本更新 key 的過期時間。

  1. private RFuture<Boolean> tryAcquireOnceAsync(long leaseTime, TimeUnit unit, long threadId) { 
  2.   if (leaseTime != -1) { 
  3.     return tryLockInnerAsync(leaseTime, unit, threadId, RedisCommands.EVAL_NULL_BOOLEAN); 
  4.   } 
  5.   RFuture<Boolean> ttlRemainingFuture = tryLockInnerAsync(commandExecutor.getConnectionManager().getCfg().getLockWatchdogTimeout(), TimeUnit.MILLISECONDS, threadId, RedisCommands.EVAL_NULL_BOOLEAN); 
  6.   ttlRemainingFuture.onComplete((ttlRemaining, e) -> { 
  7.     if (e != null) { 
  8.       return
  9.     } 
  10.  
  11.     // lock acquired 
  12.     if (ttlRemaining) { 
  13.       scheduleExpirationRenewal(threadId); 
  14.     } 
  15.   }); 
  16.   return ttlRemainingFuture; 

scheduleExpirationRenewal() 方法具體調(diào)用邏輯如下:

  1. private void renewExpiration() { 
  2.   ExpirationEntry ee = EXPIRATION_RENEWAL_MAP.get(getEntryName()); 
  3.   if (ee == null) { 
  4.     return
  5.   } 
  6.  
  7.   Timeout task = commandExecutor.getConnectionManager().newTimeout(new TimerTask() { 
  8.     @Override 
  9.     public void run(Timeout timeout) throws Exception { 
  10.       ExpirationEntry ent = EXPIRATION_RENEWAL_MAP.get(getEntryName()); 
  11.       if (ent == null) { 
  12.         return
  13.       } 
  14.       Long threadId = ent.getFirstThreadId(); 
  15.       if (threadId == null) { 
  16.         return
  17.       } 
  18.  
  19.       RFuture<Boolean> future = renewExpirationAsync(threadId); 
  20.       future.onComplete((res, e) -> { 
  21.         if (e != null) { 
  22.           log.error("Can't update lock " + getName() + " expiration", e); 
  23.           return
  24.         } 
  25.  
  26.         // reschedule itself 
  27.         renewExpiration(); 
  28.       }); 
  29.     } 
  30.   }, internalLockLeaseTime / 3, TimeUnit.MILLISECONDS); 
  31.  
  32.   ee.setTimeout(task); 

通過代碼發(fā)現(xiàn)每次鎖續(xù)期完成后又會重新創(chuàng)建新線程刷新租期。

redis lua 實現(xiàn)分布式鎖存在的問題

1、對設(shè)置有租約時間的客戶端,當長時間阻塞將導致鎖失效。

2、當 redis master 發(fā)生故障時,某 slave 升級為新 master,但鎖信息未同步到新的 master ,導致其他請求能獲取鎖。

什么是 RedLock

對于 redis 主從漂移時,將導致鎖失效的問題,redis 作者提出 RedLock 的算法:假設(shè) redis 的部署模式是 redis cluster,總共有 3個 master 節(jié)點,加鎖的時候,它會向多半節(jié)點發(fā)送 setex mykey myvalue 命令,只要過半節(jié)點成功,才算加鎖成功。同樣當釋放鎖的時候需要向所有節(jié)點發(fā)送 del 命令,感興趣的可以閱讀 Redisson 源碼實現(xiàn)。

使用 RedLock 雖解決了 master 故障帶來的同步問題,但它需要更多的 redis 實例資源,同時性能也會有一定的折損。

講講緩存穿透、擊穿、雪崩

緩存穿透:指緩存和數(shù)據(jù)庫中都沒有的數(shù)據(jù),而用戶或攻擊者不斷發(fā)起請求,如發(fā)起為 userId 為負數(shù)或不存在的數(shù)據(jù),將導致數(shù)據(jù)庫壓力過大,解決方案:

1、對參數(shù)值做有效性校驗、用戶鑒權(quán)等。

2、對緩存與數(shù)據(jù)庫中都不存在的數(shù)據(jù),可映射其 userId -> null 到緩存中,并根據(jù)業(yè)務場景設(shè)置過期時間,防止攻擊者的暴力攻擊。

緩存擊穿:指緩存中沒有數(shù)據(jù),但數(shù)據(jù)庫中有數(shù)據(jù),一般是未做熱加載或緩存過期導致,在某一刻由于并發(fā)查詢同一條數(shù)據(jù)的請求特別多,讀緩存無數(shù)據(jù),因此同時去數(shù)據(jù)庫查詢數(shù)據(jù),引起數(shù)據(jù)庫壓力瞬間增大,解決方案:

1、設(shè)置熱點數(shù)據(jù)緩存過期時間更長或永久。

2、當查詢緩存無數(shù)據(jù)時,使用互斥鎖控制只允許一個線程 A 查詢數(shù)據(jù)庫,其余請求線程等待線程 A 加載數(shù)據(jù)到緩存,如Guava Cache在查詢緩存無數(shù)據(jù)時,只允許一個線程加載。

緩存雪崩:指緩存中大批量數(shù)據(jù)到過期時間,同時查詢數(shù)據(jù)量巨大,引起數(shù)據(jù)庫壓力過大甚至宕機。與緩存擊穿不同的是,緩存擊穿是圍繞并發(fā)查詢同一條數(shù)據(jù),而緩存雪崩是不同數(shù)據(jù)都過期了,很多數(shù)據(jù)都查不到從而查數(shù)據(jù)庫,解決方案:

1、設(shè)置緩存數(shù)據(jù)的過期時間隨機,防止同一時間內(nèi)大量數(shù)據(jù)發(fā)生過期。

2、設(shè)置熱點數(shù)據(jù)過期時間更長或永久。

談談緩存和數(shù)據(jù)庫一致性問題

常見的緩存與數(shù)據(jù)庫操作順序有幾種方式:

先寫緩存,再更新 DB:

  • 如果第一步更新緩存失敗,直接返回,無影響。
  • 如果緩存寫成功,更新 DB 失敗,此時若不清除緩存中已寫入的數(shù)據(jù),則會造成數(shù)據(jù)不一致(緩存中是新值,DB 中是舊值)。如果增加清除緩存的邏輯,那么清除操作又失敗了該如何處理?

先更新 DB,再寫緩存:

  • 如果更新 DB 失敗,直接返回,無影響。
  • 如果更新 DB 成功,緩存寫入失敗則會造成數(shù)據(jù)不一致(即 DB 中是新值,緩存中是舊值),如果重試寫入緩存,那重試也失敗該如何處理?

先刪除緩存,再更新 DB:

  • 如果刪除緩存失敗,直接返回,無影響。
  • 如果刪除緩存成功,更新 DB 失敗,則會造成后續(xù)請求未命中緩存,則從數(shù)據(jù)庫中回查數(shù)據(jù)。

先更新 DB,再刪除緩存:

  • 如果更新 DB 失敗,直接返回,無影響。
  • 如果更新 DB 成功,刪除緩存失敗則會造成數(shù)據(jù)不一致(DB 中是新值,緩存中是舊值)。

該問題本質(zhì)上就是一個分布式數(shù)據(jù)一致性問題,在不要求強一致性的場景下,保證最終一致性即可,在更新完數(shù)據(jù)庫后,通過 Canal 訂閱 MySQL 的 binlog 日志使緩存失效,若操作緩存失敗,把緩存信息放至 MQ 重試。

對數(shù)據(jù)要求強一致性或無法接收臟數(shù)據(jù),最簡單的方式是不使用緩存,直接走數(shù)據(jù)庫。

redis 持久化方式哪些?

RDB,全稱 Redis Database,在指定的時間間隔內(nèi)將內(nèi)存中的數(shù)據(jù)集以快照的方式寫入磁盤,實際操作過程是 fork 一個子進程,先將數(shù)據(jù)集寫入臨時文件,寫入成功后,再替換之前的文件,用二進制壓縮存儲,在恢復數(shù)據(jù)時將快照文件直接讀到內(nèi)存里。

優(yōu)點:

  • RDB 快照是壓縮后的二進制文件,文件的大小會很小,比較適合使用全量復制與備份的場景。
  • 相比于 AOF 機制,如果數(shù)據(jù)集很大,RDB 的恢復效率會更高。

缺點:

  • 如果想保證數(shù)據(jù)的高可用性,即最大限度的避免數(shù)據(jù)丟失,那么 RDB 不是一個很好的選擇,因為系統(tǒng)一旦在定時持久化之前出現(xiàn)宕機現(xiàn)象,沒有來得及寫入磁盤的數(shù)據(jù)都將丟失。
  • 由于每次生成 RDB 快照都需要 fork 子進程生成全量數(shù)據(jù)的快照,占用 CPU 與磁盤資源,不適合于頻繁執(zhí)行。
  • 兼容問題,不同版本的 redis 生成的快照可能不兼容。

AOF,全稱為 Append Only File,將操作命令與數(shù)據(jù)以格式化的方式追加到操作日志文件的尾部,在 append 操作返回后(已經(jīng)寫入到文件或者即將寫入),才進行實際的數(shù)據(jù)變更,日志文件保存了歷史所有的操作過程,當 redis server 需要恢復數(shù)據(jù)時,可直接重放該日志文件,即可還原所有的操作過程。

在 redis 中提供每秒同步、每次修改同步、不同步3 種同步策略。實際每秒同步是異步完成的,其效率高,一旦系統(tǒng)出現(xiàn)宕機,則這一秒內(nèi)修改的數(shù)據(jù)將會丟失。

每次修改同步,即每次發(fā)生的數(shù)據(jù)變化都會被立即記錄到磁盤中,可想而至,這種同步方式效率是最低的。

優(yōu)點:

  • AOP 機制提供更高的數(shù)據(jù)安全性,即數(shù)據(jù)持久性。
  • AOF 持久化方式包含一個格式清晰、易于理解的日志內(nèi)容,用于記錄所有的修改操作。
  • 對于寫入了一半數(shù)據(jù)后出現(xiàn)了系統(tǒng)崩潰的現(xiàn)象,redis 能通過 redis-check-aof 工具幫助解決數(shù)據(jù)一致性的問題。
  • 當日志文件過大時,redis 會啟動 rewrite 機制,可以刪除其中的某些命令。

缺點:

  • 對相同數(shù)量的數(shù)據(jù)而言,AOF 文件通常要大于 RDB 文件,AOF 的恢復數(shù)據(jù)的速度要比 RDB 效率低。
  • 根據(jù)同步策略的不同,AOF 在運行效率上通常會慢于 RDB,但每秒同步策略的效率是比較高的,禁用同步策略的效率和 RDB 效率類似。

對于選擇哪種持久化方式,可根據(jù)系統(tǒng)能否接受部分性能的犧牲,通過 AOF 方式換取更高的數(shù)據(jù)一致性,或者禁用 RDB 備份換取更高的性能,待請求量或流量少的時間點再定時執(zhí)行 save 命令做快照備份,但目前生產(chǎn)環(huán)境接觸的更多都是二者結(jié)合使用的。

redis 部署方式有哪些

單機模式,即只有一個 redis 實例,所有的服務都連接到該實例上,該模式不適用于生產(chǎn)環(huán)境,若 redis 實例發(fā)生宕機或內(nèi)存不足等,將導致所有服務都受影響。

哨兵模式,redis 官方推薦的高可用性方案,在 master 宕機后,redis 本身不具備自動主備切換的功能,而 redis-sentinel 是一個獨立運行的進程,它能監(jiān)控多個 master-slave 集群,發(fā)現(xiàn) master 宕機后能自動選舉新的 master。

集群模式,隨著業(yè)務和數(shù)據(jù)量劇增,已達到單節(jié)點性能瓶頸,垂直擴容受機器限制,水平擴容涉及對業(yè)務的影響,及數(shù)據(jù)遷移時存在數(shù)據(jù)丟失的風險。

因此在 redis 3.0 推出 cluster 分布式集群方案,當遇到單節(jié)點內(nèi)存、并發(fā)、流量瓶頸時,可采用cluster 方案實現(xiàn)負載均衡,該方案主要解決分片問題,把整個數(shù)據(jù)按照規(guī)則分成多個子集存儲在多個不同 redis 節(jié)點上,每個節(jié)點各自負責整個數(shù)據(jù)的一部分。

redis 為何使用哈希槽而沒用一致性 hash

redis 集群沒有直接使用一致性哈希,而是使用哈希槽,不同點就是對于哈希空間的定義,一致性哈希的空間是一個圓環(huán),節(jié)點分布是基于圓環(huán)的,無法很好的控制數(shù)據(jù)分布,可能會產(chǎn)生數(shù)據(jù)傾斜問題。

而 redis 的槽位空間是自定義分配的,可以自定義大小,自定義位置的。redis 集群包含了 16384 個哈希槽,每個 Key 經(jīng)過 CRC16 算法計算后會落在一個具體的槽位上,而槽位具體在哪個機器上是用戶自己根據(jù)自己機器的情況配置的,機器硬盤小的可以分配少一點槽位,硬盤大的可以分配多一點。

另外在容錯性和擴展性上與一致性哈希一樣,都是轉(zhuǎn)移受影響的數(shù)據(jù)。而哈希槽本質(zhì)上是對槽位的轉(zhuǎn)移,把故障節(jié)點負責的槽位轉(zhuǎn)移到其他正常的節(jié)點上,擴展節(jié)點也是一樣,把其他節(jié)點上的槽位轉(zhuǎn)移到新的節(jié)點上。

談談數(shù)據(jù)遷移時,客戶端訪問數(shù)據(jù)的流程

當數(shù)據(jù)遷移過程中,新舊節(jié)點對應的槽都存在部分數(shù)據(jù),客戶端首先嘗試訪問舊的節(jié)點,如果對應的數(shù)據(jù)在舊節(jié)點里,舊節(jié)點正常處理。

如果不在舊節(jié)點,則可能在新節(jié)點或者不存在。當客戶端訪問舊節(jié)點不存在時,會向客戶端返回 ASK 或者 MOVED 重定向指令,其中 MOVED 是永久轉(zhuǎn)向信號,ASK 則表示只需要這一次操作做轉(zhuǎn)向。

需要注意的是,客戶端查詢新節(jié)點時,需要先發(fā)一條 ASKING 命令,否則這個請求命令會被帶有 IMPORTING 狀態(tài)的槽新節(jié)點拒絕執(zhí)行。

對于客戶端,收到 MOVED 時,需要更新 slot 映射信息,當收到 ASK 時,則需要向新節(jié)點發(fā) ASKING 命令并重新執(zhí)行操作命令。

redis 過期數(shù)據(jù)清除機制

被動刪除:當操作讀/寫一個已過期的 key 時,會觸發(fā)惰性刪除策略,直接刪除過期 key 并且返回NIL。

主動刪除:由于惰性刪除策略無法保證冷數(shù)據(jù)被及時刪掉,因此 redis 會定期主動淘汰清除已過期的 key。

redis 內(nèi)存淘汰策略

當前已用內(nèi)存超過 redis 配置的 maxmemory 限定時,會觸發(fā)主動清理策略,策略如下:

  • noeviction :不進行數(shù)據(jù)淘汰,當緩存被寫滿后,Redis不提供服務直接返回錯誤。
  • volatile-random :在設(shè)置過期時間的鍵值對中隨機刪除。
  • volatile-ttl :在設(shè)置過期時間的鍵值對,基于過期時間的先后進行刪除,越早過期的越先被刪除。
  • volatile-lru:基于LRU(Least Recently Used) 算法篩選設(shè)置了過期時間的鍵值對, 最近最少使用的原則篩選數(shù)據(jù)。
  • volatile-lfu:使用 LFU( Least Frequently Used ) 算法選擇設(shè)置了過期時間的鍵值對, 使用頻率最少的原則篩選數(shù)據(jù)
  • allkeys-random:從所有鍵值對中隨機選擇并刪除數(shù)據(jù)。
  • allkeys-lru:使用 LRU 算法在所有數(shù)據(jù)中進行篩選。
  • allkeys-lfu:使用 LFU 算法在所有數(shù)據(jù)中進行篩選。

線上 redis 實例內(nèi)存不足,該如何處理

這是在面試騰訊音樂時被問到的問題,考察個人應急問題處理能力,首先第一要素是解決問題,即線上擴容,不能影響用戶功能使用,但線上擴容只是解燃眉之急,后面數(shù)據(jù)增加后不可能繼續(xù)擴容,畢竟成本擺在那里,因此可使用 redis cluster 方案把數(shù)據(jù)均衡的分布存儲在不同的 redis 實例中,解決 redis 單實例存儲過高的問題,但使用 redis cluster 方案也會引入一定的問題,例如某些命令不能在 cluster 下執(zhí)行,增加數(shù)據(jù)遷移復雜度等。 

 

責任編輯:武曉燕 來源: 碼農(nóng)私房話
相關(guān)推薦

2021-11-02 11:35:17

通信進程面試

2010-08-11 12:07:08

騰訊筆試題騰訊筆試題

2024-05-23 16:41:40

2020-07-17 20:35:41

Redis數(shù)據(jù)庫緩存

2024-12-19 17:09:55

Redis哨兵模式數(shù)據(jù)庫

2024-04-18 08:00:00

腦裂問題Redis哨兵模式

2013-12-03 09:32:19

2024-06-03 06:45:18

2021-10-27 11:00:30

C++語言面試

2009-02-26 10:33:08

面試求職計算機專業(yè)

2019-02-18 13:36:03

Redis數(shù)據(jù)庫面試

2021-10-18 08:41:20

Redis ACID事務

2024-04-30 10:40:11

2018-01-11 16:43:32

面試騰訊職位

2021-02-23 12:43:39

Redis面試題緩存

2018-11-19 10:40:17

騰訊馬化騰互聯(lián)網(wǎng)

2013-06-18 10:12:39

程序員未來

2009-02-20 16:21:18

UbuntuLinux中國化

2020-11-16 07:22:32

騰訊多線程

2020-11-12 10:20:40

前端面試web
點贊
收藏

51CTO技術(shù)棧公眾號