LFU Cache

题目:
Design and implement a data structure for Least Frequently Used (LFU) cache. It should support the following operations: get and put.

get(key) - Get the value (will always be positive) of the key if the key exists in the cache, otherwise return -1.
put(key, value) - Set or insert the value if the key is not already present. When the cache reaches its capacity, it should invalidate the least frequently used item before inserting a new item. For the purpose of this problem, when there is a tie (i.e., two or more keys that have the same frequency), the least recently used key would be evicted.

Follow up:
Could you do both operations in O(1) time complexity?

Example:

LFUCache cache = new LFUCache( 2 /* capacity */ );

cache.put(1, 1);
cache.put(2, 2);
cache.get(1); // returns 1
cache.put(3, 3); // evicts key 2
cache.get(2); // returns -1 (not found)
cache.get(3); // returns 3.
cache.put(4, 4); // evicts key 1.
cache.get(1); // returns -1 (not found)
cache.get(3); // returns 3
cache.get(4); // returns 4
思路:
定义一个结构体来表示cache中的数据的key-value和使用频率:

typedef struct Node{        //使用typedef将数据类型struct Node重命名为Node  
        int key;
        int value;
        int frequency;
        Node(int k,int v,int f){    //结构体构造函数 
            key = k;
            value = v;
            frequency = f;
        }
    }Node;

使用动态数组来保存cache中的数据,执行put时,分为三种情况:1、key不存在且内存够时,2、key不存在内存不够时,3、key存在时。
第一种情况时直接将这个数据加到数组最后,第二种情况时要删除使用频率少且最近最不使用的,第三种情况要修改数据的频率。注意put时,三种情况下都要将这个数据放在数组最后。get方法注意get后要增加频率并把对应的数据删除再放到数组最后。
注意边界条件:capacity == 0时,直接 return

代码:

#include<iostream>
#include<string.h>
#include<vector>

using namespace std;

class FLUCache{
#define MAX 99999999
public:
    typedef struct Node{
        int key;
        int value;
        int frequency;
        Node(int k,int v,int f){
            key = k;
            value = v;
            frequency = f;
        }
    }Node;
    vector<Node> recent;
    int capacity;
    int size;
    FLUCache(int c){
        capacity = c;
        size = 0;
    }
    //获取cache中的数据的value 
    int get(int key){
        int index = findKey(key);
        if(index != -1){
            int curFrequency = recent.at(index).frequency;
            int value = recent.at(index).value;
            recent.erase(recent.begin()+index);
            recent.push_back(Node(key,value,++curFrequency));
            return value;
        }else{
            return -1;
        }
    }
    //向cache中放数据 
    void put(int key,int value){
        if(capacity == 0) return;
        int index = findKey(key);
        //key不存在切容量未满 
        if(index == -1 && size < capacity){
            recent.push_back(Node(key,value,1));
            size++;
        }else if(index == -1 && size == capacity){  //key不存在,容量满 
            int index = findLeastFrequencyAndUsed();
            //删除最少频率和最近不使用的 
            recent.erase(recent.begin()+index);
            recent.push_back(Node(key,value,1)); 
        }else if(index != -1){  //key存在
            int curFrequency = recent.at(index).frequency;
            recent.erase(recent.begin()+index);
            recent.push_back(Node(key,value,++curFrequency));
        }
    }
    //获取查找数据的数组中的索引 
    int findKey(int key){
        int i;
        for(i = 0; i < recent.size(); i++){
            struct Node node = recent.at(i);
            if(key == node.key){
                return i;
            } 
        }
        return -1;
    }
    //查找需要驱逐的数据在数组中的索引 
    int findLeastFrequencyAndUsed(){
        int i,index;
        index = 0;
        int minFrequency = MAX;
        for(i = 0; i < recent.size(); i++){
            Node node = recent.at(i);
            if(node.frequency < minFrequency){
                minFrequency = node.frequency;
                index = i;
            }
        }
        return index;
    } 
};
int main(){
    FLUCache *cache = new FLUCache(2);
    cache->put(1,1);
    cache->put(2, 2);
    cout<<cache->get(1)<<endl;       // returns 1
    cache->put(3, 3);    // evicts key 2
    cout<<cache->get(2)<<endl;       // returns -1 (not found)
    cout<<cache->get(3)<<endl;       // returns 3.
    cache->put(4, 4);    // evicts key 1.
    cout<<cache->get(1)<<endl;       // returns -1 (not found)
    cout<<cache->get(3)<<endl;       // returns 3
    cout<<cache->get(4)<<endl;       // returns 4
    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值