インタビューの質問16.25。LRUキャッシュ

LRU:最も最近使用された

それについては、オペレーティングシステムのクラスで話しました。全体としてスタックが使用され、新しく使用されたものが抽出され、スタックの一番上に置かれます。スタックサイズが制限に達した場合は、スタックの一番下を削除します。

もちろん、この時間の複雑さは高すぎます。ルックアップ時間O(n)、更新時間O(n)。

上記の2つの演算の時間の複雑さがO(1)に到達する場合。考える:O(1)を探す、つまり、それが存在するかどうかを見つけるためのキー、O(1)時間がある、確かにハッシュテーブルはエスケープできない。

また、時間順に並べ替えます。最近使用したものが最初に使用され、最も古いものが最後に使用されます。ただし、毎回検出されるノードは途中にある可能性があるため、動的な挿入と削除、つまりリンクリストが必要です。

 

だから全体的に:

リンクリストにはKey-Valueが格納されます。そして、最も新しいものから最も古いものまでの出現時間に従って配置されます(最新の発生はリンクされたリストの先頭にあります)。

ハッシュテーブルもあり、keyはリンクリストノードのキー、valueはキーに対応するリンクリストノード項目(ポインタまたはイテレータ)です。

このようにして、対応するリンクリストノードは、ハッシュテーブルを介してO(1)時間で見つけることができます。更新時には、ノードをリンクリストの先頭に直接移動し、ハッシュテーブルのマッピング関係を更新します。この操作もO(1)です。

タイトル:

最も最近使用されていないアイテムを削除する「最近使用されていない」キャッシュを設計および構築します。キャッシュはキーから値にマップし(特定のキーに対応する値を挿入および取得できるようにする)、初期化時の最大容量を指定する必要があります。キャッシュがいっぱいになると、最も使用頻度の低いアイテムが削除されます。

次の操作をサポートする必要があります。

Get data get(key)-キー(key)がキャッシュに存在する場合は、キーの値を取得し(常に正の数)、それ以外の場合は-1を返します。
書き込みデータの書き込み(キー、値)-キーが存在しない場合は、そのデータ値を書き込みます。キャッシュ容量が上限に達すると、新しいデータを書き込む前に、最も最近使用されていないデータ値を削除して、新しいデータ値のための余地を残します。

例:

LRUCacheキャッシュ=新しいLRUCache(2 / *キャッシュ容量* /);

cache.put(1、1);
cache.put(2、2);
cache.get(1); // 1を返します
cache.put(3、3); //この操作により、キー2が無効になります
。 get(2); // -1(見つかりません)を返します
cache.put(4、4); //この操作はキー1を無効にします
cache.get(1); // -1(見つかりません)を返します
cache .get(3); // 3を返します
cache.get(4); // 4を返します

 

回答:

クラスLRUCache {
 public 
    unordered_map < int、list <pair < intint >> :: iterator> mp; 
    リスト <pair < intint >> data;
    int n; 
    LRUCache(int capacity){ 
        n = 容量; 
    } 
    
    int  getint key){
         if (mp.count(key)){ 
            put(key、mp [key] -> second);
            mp [key]-> 
        }を返す秒をます。
         return - 1 ; 
    } 
    
    void put(int key、int value){
         if (mp.count(key)){ 
            auto iter = mp [key]; 
            data.push_front({key、value}); // リンクリストに更新ヘッダー 
            data.erase(iter); // 前のイテレーターを削除 
            mp [key] = data.begin(); 
        } 
        else {
             if(data.size()> = n){ 
                auto p = data.back() ; 
                mp.erase(p.first); 
                data.pop_back();
            } 
            data.push_front({key、value}); 
            mp [key] = data.begin(); 
        } 
    } 
}; 

/ * * 
 * LRUCacheオブジェクトがインスタンス化され、次のように呼び出されます。
 * LRUCache * obj = new LRUCache(capacity); 
 * int param_1 = obj-> get(key); 
 * obj-> put(key、value); 
 * /

 

おすすめ

転載: www.cnblogs.com/FdWzy/p/12741908.html