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

Python之LRU緩存應(yīng)用與實(shí)例

 更新時(shí)間:2025年10月09日 08:43:36   作者:AI手記叨叨禮拜天  
LRU(最近最少使用)是高效緩存淘汰算法,通過(guò)OrderedDict維護(hù)訪問(wèn)順序,實(shí)現(xiàn)O(1)時(shí)間復(fù)雜度的get/put操作,適用于Web應(yīng)用和配置管理,但不適用于強(qiáng)一致性場(chǎng)景或超大數(shù)據(jù)集

一、什么是LRU

LRU(Least Recently Used,最近最少使用)是一種常用的緩存淘汰算法,用于在緩存空間不足時(shí)決定哪些數(shù)據(jù)應(yīng)該被移除。

核心思想

如果一個(gè)數(shù)據(jù)最近被訪問(wèn)過(guò),那么它將來(lái)被訪問(wèn)的概率也更高。因此,當(dāng)緩存空間不足時(shí),應(yīng)該優(yōu)先淘汰最久未被訪問(wèn)的數(shù)據(jù)。

工作原理

訪問(wèn)數(shù)據(jù)時(shí)

  • 如果數(shù)據(jù)在緩存中(緩存命中),則將該數(shù)據(jù)標(biāo)記為"最近使用",并移動(dòng)到緩存的最前面(或最后面,取決于實(shí)現(xiàn))。
  • 如果數(shù)據(jù)不在緩存中(緩存未命中),則從原始數(shù)據(jù)源加載。

緩存滿(mǎn)時(shí)

  • 需要插入新數(shù)據(jù)時(shí),移除最久未被訪問(wèn)的數(shù)據(jù)(即LRU數(shù)據(jù)),
  • 然后插入新數(shù)據(jù)到最新位置。

主要特性

  • 固定容量:限制緩存大小,防止內(nèi)存無(wú)限增長(zhǎng)。
  • 自動(dòng)淘汰機(jī)制:當(dāng)緩存滿(mǎn)時(shí),移除最舊的條目。
  • 快速訪問(wèn):get()put() 操作的時(shí)間復(fù)雜度均為 O(1)。
  • 保持訪問(wèn)順序:每次訪問(wèn)或更新緩存條目時(shí),會(huì)將其移至最新位置。

二、核心實(shí)現(xiàn)

1. 數(shù)據(jù)結(jié)構(gòu)

使用 OrderedDict 存儲(chǔ)鍵值對(duì),并維護(hù)訪問(wèn)順序:

  • 最新訪問(wèn)的條目 位于字典的末尾。
  • 最久未訪問(wèn)的條目 位于字典的開(kāi)頭。

2. 關(guān)鍵方法

__init__(self, capacity)

初始化緩存,設(shè)置最大容量。

  • 參數(shù): capacity (int):緩存的最大條目數(shù)。
  • 示例:
cache = LatestCache(1000)  # 最大存儲(chǔ) 1000 個(gè)條目

get(self, key)

獲取緩存中的值,如果不存在則返回 None。

  • 參數(shù): key:要查詢(xún)的鍵。
  • 返回值: 如果存在,返回對(duì)應(yīng)的值;否則返回 None。
  • 示例:
value = cache.get("some_key")

put(self, key, value)

向緩存中添加或更新鍵值對(duì)。

  • 參數(shù): key:要存儲(chǔ)的鍵; value:要存儲(chǔ)的值。
  • 行為: 如果 key 已存在,更新其值并移至最新位置; 如果緩存已滿(mǎn),移除最舊的條目。
  • 示例:
cache.put("some_key", "some_value")

三、使用示例

1. 基本用法

from collections import OrderedDict

class LatestCache:
    def __init__(self, capacity):
        self.cache = OrderedDict()
        self.capacity = capacity

    def get(self, key):
        if key not in self.cache:
            return None
        self.cache.move_to_end(key)  # 移至最新位置
        return self.cache[key]

    def put(self, key, value):
        if key in self.cache:
            self.cache.move_to_end(key)  # 更新時(shí)移至最新位置
        self.cache[key] = value
        if len(self.cache) > self.capacity:
            self.cache.popitem(last=False)  # 移除最舊的條目


# 初始化緩存
cache = LatestCache(3)

# 添加數(shù)據(jù)
cache.put("a", 1)
cache.put("b", 2)
cache.put("c", 3)

# 查詢(xún)數(shù)據(jù)
print(cache.get("a"))  # 輸出: 1

# 緩存滿(mǎn)時(shí)自動(dòng)淘汰
cache.put("d", 4)      # 淘汰最久未訪問(wèn)的鍵 "b"
print(cache.get("b"))  # 輸出: None(已被淘汰)

2. 適用場(chǎng)景

  • 高頻讀取、低頻寫(xiě)入:如配置緩存、靜態(tài)數(shù)據(jù)緩存。
  • 減少重復(fù)計(jì)算:如函數(shù)結(jié)果緩存。
  • 優(yōu)化數(shù)據(jù)庫(kù)/API 查詢(xún):緩存熱點(diǎn)數(shù)據(jù),減少 IO 開(kāi)銷(xiāo)。

四、優(yōu)化建議

1. 線程安全改進(jìn)

當(dāng)前實(shí)現(xiàn) 非線程安全,多線程環(huán)境下可能導(dǎo)致數(shù)據(jù)競(jìng)爭(zhēng)??梢?threading.RLock 加鎖:

from threading import RLock

class LatestCache:
    def __init__(self, capacity):
        self._lock = RLock()
        self.cache = OrderedDict()
        self.capacity = capacity

    def get(self, key):
        with self._lock:
            if key not in self.cache:
                return None
            self.cache.move_to_end(key)
            return self.cache[key]

    def put(self, key, value):
        with self._lock:
            if key in self.cache:
                self.cache.move_to_end(key)
            self.cache[key] = value
            if len(self.cache) > self.capacity:
                self.cache.popitem(last=False)

2. 緩存命中率統(tǒng)計(jì)

增加 hitsmisses 統(tǒng)計(jì),評(píng)估緩存效率:

  • hits: 記錄成功從緩存中獲取數(shù)據(jù)的次數(shù)
  • misses: 記錄未能從緩存中獲取數(shù)據(jù)的次數(shù)
  • cache: 使用OrderedDict實(shí)現(xiàn)的緩存存儲(chǔ),保持鍵的插入順序
  • capacity: 緩存的最大容量
from threading import RLock
from collections import OrderedDict


class LatestCache:
    def __init__(self, capacity):
        self._lock = RLock()
        self.hits = 0
        self.misses = 0
        self.cache = OrderedDict()
        self.capacity = capacity

    def get(self, key):
        with self._lock:
            if key in self.cache:
                self.hits += 1
                self.cache.move_to_end(key)
                return self.cache[key]
            self.misses += 1
            return None

    def put(self, key, value):
        with self._lock:
            if key in self.cache:
                self.cache.move_to_end(key)
            self.cache[key] = value
            if len(self.cache) > self.capacity:
                self.cache.popitem(last=False)

    def hit_rate(self):
        with self._lock:
            total = self.hits + self.misses
            return (self.hits / total) if total > 0 else 0.0


# 初始化緩存
cache = LatestCache(3)

# 添加數(shù)據(jù)
cache.put("a", 1)
cache.put("b", 2)
cache.put("c", 3)

# 查詢(xún)數(shù)據(jù)
print(cache.get("a"))  # 命中,輸出: 1
print(cache.get("b"))  # 命中,輸出: 2
print(cache.get("a"))  # 命中,輸出: 1
print(cache.get("x"))  # 未命中,輸出: None

# 緩存滿(mǎn)時(shí)自動(dòng)淘汰
cache.put("d", 4)  # 淘汰最久未訪問(wèn)的鍵 "c"
print(cache.get("c"))  # 未命中(已被淘汰),輸出: None

# 查看命中率統(tǒng)計(jì)
print(f"命中次數(shù): {cache.hits}")  # 輸出: 3 (aba)
print(f"未命中次數(shù): {cache.misses}")  # 輸出: 2 (xc)
print(f"命中率: {cache.hit_rate():.2%}")  # 輸出: 60.00% (3命中/(3命中+2未命中))

3. 支持 TTL

TTL(Time To Live)是數(shù)據(jù)在緩存中存活的生存時(shí)間,過(guò)期后自動(dòng)失效。

from collections import OrderedDict
import time
import random


class LatestCache:
    def __init__(self, capacity):
        self.cache = OrderedDict()
        self.capacity = capacity

    def get(self, key):
        if key not in self.cache:
            return None
        value, expire_time = self.cache[key]
        if expire_time and time.time() > expire_time:
            del self.cache[key]  # 自動(dòng)清理過(guò)期數(shù)據(jù)
            return None
        self.cache.move_to_end(key)  # 更新為最近使用
        return value

    def put(self, key, value, ttl=None):
        expire_time = time.time() + ttl if ttl else None
        if key in self.cache:
            self.cache.move_to_end(key)
        self.cache[key] = (value, expire_time)
        if len(self.cache) > self.capacity:
            self.cache.popitem(last=False)  # 移除最久未使用的


# 初始化緩存(容量為3)
cache = LatestCache(3)

# 添加數(shù)據(jù)(帶TTL和不帶TTL的混合)
cache.put("a", 1, ttl=2)  # 2秒后過(guò)期
cache.put("b", 2)  # 永不過(guò)期
cache.put("c", 3, ttl=4)  # 4秒后過(guò)期

# 立即查詢(xún)(全部命中)
print(f"初始查詢(xún): a={cache.get('a')}, b={cache.get('b')}, c={cache.get('c')}")
# 輸出: 初始查詢(xún): a=1, b=2, c=3

# 模擬2秒后('a'已過(guò)期)
print("等待2秒后...")
time.sleep(2)

print(f"查詢(xún): a={cache.get('a')}, b={cache.get('b')}, c={cache.get('c')}")
# 輸出: 查詢(xún): a=None , b=2, c=3

五、總結(jié)

1. 優(yōu)點(diǎn)

  • 簡(jiǎn)單高效:基于 OrderedDict,get()put() 均為 O(1) 時(shí)間復(fù)雜度。
  • 自動(dòng)淘汰:LRU 策略防止內(nèi)存無(wú)限增長(zhǎng)。
  • 易于擴(kuò)展:可增加 TTL、線程安全、命中統(tǒng)計(jì)等功能。

2. 適用場(chǎng)景

  • Web 應(yīng)用:緩存 API 響應(yīng)、數(shù)據(jù)庫(kù)查詢(xún)結(jié)果。
  • 計(jì)算密集型任務(wù):緩存中間計(jì)算結(jié)果,避免重復(fù)計(jì)算。
  • 配置管理:緩存頻繁讀取的配置數(shù)據(jù)。

3. 不適用場(chǎng)景

  • 強(qiáng)一致性要求:緩存可能導(dǎo)致數(shù)據(jù)短暫不一致,如緩存更新延遲、緩存失效策略、分布式環(huán)境同步等。
  • 超大數(shù)據(jù)集:?jiǎn)螜C(jī)內(nèi)存有限,可改用 Redis 等分布式緩存。

以上為個(gè)人經(jīng)驗(yàn),希望能給大家一個(gè)參考,也希望大家多多支持腳本之家。

相關(guān)文章

  • 關(guān)于Python dict存中文字符dumps()的問(wèn)題

    關(guān)于Python dict存中文字符dumps()的問(wèn)題

    這篇文章主要介紹了關(guān)于Python dict存中文字符dumps()的問(wèn)題,本文給大家分享問(wèn)題及解決方案,給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2021-10-10
  • 淺談python浮點(diǎn)數(shù)比較的三種方法

    淺談python浮點(diǎn)數(shù)比較的三種方法

    在 Python 中,由于浮點(diǎn)數(shù)在計(jì)算機(jī)內(nèi)部的表示方式是二進(jìn)制的,因此進(jìn)行浮點(diǎn)數(shù)比較時(shí)可能會(huì)出現(xiàn)精度問(wèn)題,本文就介紹了三種解決方法,具有一定的參考價(jià)值,感興趣的可以了解一下
    2023-09-09
  • Python面向?qū)ο蟪绦蛟O(shè)計(jì)類(lèi)變量與成員變量、類(lèi)方法與成員方法用法分析

    Python面向?qū)ο蟪绦蛟O(shè)計(jì)類(lèi)變量與成員變量、類(lèi)方法與成員方法用法分析

    這篇文章主要介紹了Python面向?qū)ο蟪绦蛟O(shè)計(jì)類(lèi)變量與成員變量、類(lèi)方法與成員方法用法,結(jié)合實(shí)例形式較為詳細(xì)的分析了類(lèi)變量與成員變量、類(lèi)方法與成員方法、類(lèi)方法與靜態(tài)方法等概念、原理及使用技巧,需要的朋友可以參考下
    2019-04-04
  • Python中functools.partial設(shè)置回調(diào)函數(shù)處理異步任務(wù)使用

    Python中functools.partial設(shè)置回調(diào)函數(shù)處理異步任務(wù)使用

    本文主要介紹了Python中functools.partial設(shè)置回調(diào)函數(shù)處理異步任務(wù)使用,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2025-12-12
  • python寫(xiě)的本地WIFI密碼查看器的具體代碼

    python寫(xiě)的本地WIFI密碼查看器的具體代碼

    本文主要分享一個(gè)本地wifi密碼查看器,用python實(shí)現(xiàn)的,代碼簡(jiǎn)單易懂,感興趣的朋友跟隨小編一起看看吧
    2024-06-06
  • python 無(wú)損批量壓縮圖片(支持保留圖片信息)的示例

    python 無(wú)損批量壓縮圖片(支持保留圖片信息)的示例

    這篇文章主要介紹了python 無(wú)損批量壓縮圖片的示例,幫助大家更好的利用python處理圖片,感興趣的朋友可以了解下
    2020-09-09
  • Python Selenium參數(shù)配置方法解析

    Python Selenium參數(shù)配置方法解析

    這篇文章主要介紹了Python Selenium參數(shù)配置方法解析,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2020-01-01
  • Python簡(jiǎn)單讀取json文件功能示例

    Python簡(jiǎn)單讀取json文件功能示例

    這篇文章主要介紹了Python簡(jiǎn)單讀取json文件功能,結(jié)合實(shí)例形式分析了Python文件讀取及json格式數(shù)據(jù)相關(guān)操作技巧,需要的朋友可以參考下
    2017-11-11
  • 一文教你利用Python制作一個(gè)生日提醒

    一文教你利用Python制作一個(gè)生日提醒

    在國(guó)內(nèi),大部分人都是過(guò)農(nóng)歷生日,然后借助日歷工具獲取農(nóng)歷日期對(duì)應(yīng)的陽(yáng)歷日期,以這一天來(lái)過(guò)生!這里還有一個(gè)痛點(diǎn),即:每一年的農(nóng)歷生日對(duì)應(yīng)的陽(yáng)歷日期都不一樣,本篇文章將教你利用 Python 制作一個(gè)簡(jiǎn)單的生日提醒,需要的可以參考一下
    2022-12-12
  • Python+OpenCV繪制多instance的Mask圖像

    Python+OpenCV繪制多instance的Mask圖像

    Mask圖像中,不同值表示不同的實(shí)例(instance)。本文將詳細(xì)為大家講講如何利用OpenCV繪制多instance的Mask圖像,感興趣的可以學(xué)習(xí)一下
    2022-06-06

最新評(píng)論

西峡县| 九江市| 吉林省| 寿光市| 望都县| 沅陵县| 阿拉善左旗| 敦煌市| 平遥县| 新晃| 岚皋县| 庄浪县| 莒南县| 鹤峰县| 兴仁县| 鸡东县| 江永县| 桓台县| 遵义县| 修文县| 山西省| 桓台县| 昌邑市| 高要市| 高淳县| 黄陵县| 洪雅县| 静宁县| 建瓯市| 宣城市| 红桥区| 涡阳县| 饶河县| 奈曼旗| 庆城县| 越西县| 芮城县| 饶阳县| 潍坊市| 云梦县| 高雄市|