LRU缓存机制

insertTail尾插

1。如果大小为0,就更新头尾节点

2。如果大小不为0且没有满的情况下,尾插法

movetoend把节点移到最后

1.如果尾部已经要操作的结点,不动;如果是头结点换到尾部,更换头结点;结点的前一个的next指向这个节点的next,这个节点的pre是尾结点,那么尾指向它,这个节点指向NULL

get函数

如果map中有这个键,就取出这个值并移到最后。没有返回NULL

set函数

如果map中有就把这个节点移到最后,没有的话就新建一个结点并put进去

判断是否满了,如果满了就把头删了,并把map中对应的节点所在的信息删了。

class Node
{
public:
    int key;
    int value;
    Node(int key,int value)
    {
        this->key=key;
        this->value=value;
    }
};

class Link
{
public:
    Node* val;
    Link* pre;
    Link* next;
    Link(Node *val,Link *pre,Link *next )
    {
        this->val=val;
        this->pre=pre;
        this->next=next;
    }
};


class LRUCache {
public:
    Link* linkhead;
    Link* linkTail;
    int maxsize;
    int cursize;
    unordered_map<int,Link*>mmap;
public:
    LRUCache(int capacity) {
        linkhead=new Link( NULL,NULL,NULL );
        linkTail=linkhead;
        maxsize=capacity;
        cursize=0;
    }
    //插入节点
    void insertTail(Link* link)
    {
        //如果没有头
        if(cursize==0)
        {
            linkhead=link;
            linkTail=link;
        }
        //否则尾插
        else
        {
            link->pre=linkTail;
            linkTail->next=link;
            linkTail=linkTail->next;
            linkTail->next=NULL;
        }
        cursize++;
    }

    void movetoend(Link* link)
    {

        //如果是尾 不动
        if(link->val==linkTail->val)
        {
            
        }
        //如果是头 就要改变头
        else if(link->val==linkhead->val)
        {
            Link *temp=linkhead;
            linkhead=linkhead->next;
            linkhead->pre=NULL;
            temp->pre=linkTail;
            linkTail->next=temp;
            linkTail=linkTail->next;
            linkTail->next=NULL;
        }
        //如果在中间
        else{
            Link *temp=link;
            temp->pre->next=temp->next;
            temp->next->pre=temp->pre;
            temp->pre=linkTail;
            temp->next=NULL;
            linkTail->next=temp;
            linkTail=linkTail->next;
        }

    }
    
    int get(int key) {
        // Link* temp=linkhead;
        // while(temp)
        // {
        //     cout<<temp->val->key;
        //     temp=temp->next;
        // }
        // cout<<endl;
        if(mmap.count(key)==0)
        {
            return -1;
        }
        else
        {
            Link *res=mmap[key];
            //cout<<res->val->value<<endl;
            movetoend(res);
            return res -> val->value;
        }
        return 0;
        
    }
    
    void put(int key, int value) {
        // Link* temp1=linkhead;
        // while(temp1&&temp1->val)
        // {
        //    cout<<temp1->val->key;
        //     temp1=temp1->next;
        // }
        // cout<<endl;
        if(mmap.count(key)==0)
        {
            Node* node=new Node(key,value);
            Link *temp=new Link(node,NULL,NULL);
            insertTail(temp);
            mmap[key]=temp;
            if(cursize>maxsize)
            {
                Link* del=linkhead;
                //cout<<del->val->key<<endl;
                auto ite=mmap.find(del->val->key);
                mmap.erase(ite);
                linkhead=linkhead->next;
                del->pre=NULL;
                del->next=NULL;
                delete del;
                del=NULL;
                cursize--;
            }
        }
        else
        {
            mmap[key]->val->value=value;
            movetoend( mmap[key] );
        }
    }
};


/*
["LRUCache","put","put","put","put","get","get","get","get","put","get","get","get","get","get"]
[[3],[1,1],[2,2],[3,3],[4,4],[4],[3],[2],[1],[5,5],[1],[2],[3],[4],[5]]
*/
/**
 * Your LRUCache object will be instantiated and called as such:
 * LRUCache* obj = new LRUCache(capacity);
 * int param_1 = obj->get(key);
 * obj->put(key,value);
 */

  

posted @ 2020-08-19 09:44  肉松松松松  阅读(105)  评论(0)    收藏  举报