LRU缓存C++实现

LRU是一种缓存淘汰算法,淘汰原则是将最近不常访问的数据删除。
LRU缓存C++实现_第1张图片
程序使用双向链表+unordered_map,unordered_map实现O(1)的查找效率。用类LRU对双向链表和unordered_map进行封装,对外提供构造函数,插入函数Insert(int key, int value),获取值函数Getvalue(int key),获取大小函数Getsize(),获取容量函数Getcapacity()。

代码如下:

#include
#include  
using namespace std;

//节点结构体
struct node{
     
	int m_key;
	int m_value;
	node *pre;
	node *next;
	node(int key, int value) :
		m_key(key),
		m_value(value),
		pre(nullptr),
		next(nullptr){
     }
};

//LRU缓存实现类,双向链表
class LRU{
     
public:
	LRU(int size);
	~LRU();
	void Insert(int key, int value);
	int Getvalue(int key);
	int Getsize();
	int Getcapacity();
private:
	int m_capacity;
	node *phead;
	node *ptail;
	unordered_map<int, node*> mp;
	void Remove(node *pnode);
	void Sethead(node *pnode);
};

LRU::LRU(int size){
     
	m_capacity = size;
	phead = nullptr;
	ptail = nullptr;
}

LRU::~LRU(){
     
	auto it = mp.begin();
	//删除mp
	while (it != mp.end()){
     
		delete it->second;
		it->second = nullptr;
		mp.erase(it++);    //关联容器删除后迭代器失效,所以使用删除之前的迭代器定位下一个元素
	}
}

//移除
void LRU::Remove(node *pnode){
     
	if (pnode == phead){
     
		phead = phead->next;
		if (phead != nullptr){
                //防止只有一个节点Remove出错
			phead->pre = nullptr;
		}
	}
	else if (pnode == ptail){
     
		ptail = ptail->pre;
		if (ptail != nullptr){
     
			ptail->next = nullptr;
		}
	}
	else{
     
		pnode->pre->next = pnode->next;
		pnode->next->pre = pnode->pre;
	}
}

//节点放在头部
void LRU::Sethead(node *pnode){
     
	pnode->next = phead;
	pnode->pre = nullptr;
	if (phead != nullptr){
     
		phead->pre = pnode;
	}
	phead = pnode;
	if (ptail == nullptr){
     
		ptail = pnode;
	}
}

//插入数据
void LRU::Insert(int key, int value){
     
	auto it = mp.find(key);
	if (it == mp.end()){
     
		node *pnode = new node(key, value);
		Sethead(pnode);
		mp[key] = pnode;
	}
	else{
     
		it->second->m_value = value;
		Remove(it->second);
		Sethead(it->second);
	}
	if (mp.size() > m_capacity){
     
		auto it = mp.find(ptail->m_key);
		Remove(it->second);
		delete it->second;
		it->second = nullptr;
		mp.erase(it);
	}
}

//获取数据
int LRU::Getvalue(int key){
     
	auto it = mp.find(key);
	if (it != mp.end()){
     
		auto no = it->second;
		Remove(no);
		Sethead(no);
		return it->second->m_value;
	}
	else{
     
		return -1;
	}
}

int LRU::Getsize(){
     
	return mp.size();
}

int LRU::Getcapacity(){
     
	return m_capacity;
}

void main(){
     
	LRU mylru(3);
	mylru.Insert(1, 10);
	mylru.Insert(3, 20);
	mylru.Insert(5, 30);
	cout << mylru.Getvalue(1) << endl;
	mylru.Insert(7, 40);
	cout << mylru.Getvalue(1) << endl;
	cout << mylru.Getvalue(3) << endl;
	cout << mylru.Getvalue(5) << endl;
	cout << mylru.Getvalue(7) << endl;
	cout << mylru.Getsize() << endl
}

测试结果:

LRU缓存C++实现_第2张图片

你可能感兴趣的:(lru,c++,缓存)