900字范文,内容丰富有趣,生活中的好帮手!
900字范文 > lru算法c语言实现单链表 操作系统之LRU算法 C语言链表实现

lru算法c语言实现单链表 操作系统之LRU算法 C语言链表实现

时间:2022-03-07 18:15:36

相关推荐

lru算法c语言实现单链表 操作系统之LRU算法 C语言链表实现

LRU是Least Recently Used的缩写,即最近最少使用,是一种常用的页面置换算法,选择最近最久未使用的页面予以淘汰。该算法赋予每个页面一个访问字段,用来记录一个页面自上次被访问以来所经历的时间 t,当须淘汰一个页面时,选择现有页面中其 t 值最大的,即最近最少使用的页面予以淘汰。

为什么要使用链表实现呢,因为这个页面不会很多,内存和资源开销都小

在计算机中,开销往往是需要考虑的,我们不希望占用过多的系统资源,动态路由小型网络使用RIP(Bellman-Ford Routing Algorithm),大型网络设备用的就是OSPF(dijkstra),当然也有很多方面的考虑,比如RIP配置和管理更简单,RIP为了避免出现网络延迟太高,也将路由器最大的允许跳数设为15

我们存储的时候就按照时间吧,末尾为刚刚使用的,淘汰前面的

然后我们来考虑下这个算法,保证我们不使用无关变量。这个cache是空的

进行一次请求需要查看我当前的cache里是否存在这个数据

1存在

存在就比较简单了,直接取出数据,页面数据不变,并把这个结点放在最后

2不存在

2.1cache满

把最靠前的页面用读取数据的数据覆盖,然后把它放到最后的cache

2.2cache不满

直接去读取数据,然后把他放在最后的页面

我需要维护的是一个编号(或者说地址)还有后结点,然后查询肯定是O(1)的,这是内部完成的,不需要我考虑(直接得到地址去取数据)

缺页中断都对应了一个硬件操作,就是去取这个数据

#include #includestructnode

{intid;struct node *next;

}* head, *tail, *p;voidPushBack()

{/*pre没有意义,仅需要多保留一个尾结点

p->pre = tail; //使pre指向前一个节点,循环可得到反向链表*/p->next =NULL;

tail->next =p;

tail=p;

}voidfun()

{struct node *q;

q=head;while (q->next !=NULL)

{if (q->next->id == p->id)//不缺页

{

PushBack();

p= q->next;

q->next = p->next;free(p);return; //执行完全部操作停掉

}

q= q->next;

}

printf("发生缺页中断 %d\n",p->id);

PushBack();

p= head->next;

head->next = p->next;free(p);

}intmain()

{intsum, n, i;

sum= 0; //初始cache内没有数据

scanf("%d", &n); //读入页数

head = (struct node *)malloc(sizeof(structnode));

head->next =NULL;

tail=head;while (1)

{

p= (struct node *)malloc(sizeof(structnode));

scanf("%d", &p->id);if (p->id < 0)

{break;

}else{if (sum < n) //cache未满,放至后面

{

PushBack();

printf("发生缺页中断 %d\n",p->id);

sum+= 1; //并对cache+1

}else{

fun();

}

}

}return 0;

}

事后来看,我说pre没有意义是不对的,因为实际上并不是乱序的,往往我们先访问的到的会被继续访问,并不是一个完全的均摊复杂度。

所以应该记录pre进行倒序,有兴趣的可以实现一下,不过我还是觉得c++好写,但是内部肯定是更厉害的

c++实现就用list搞一下啊,把最近访问的放到最前面

#include#includevoid fun(std::list&L,intx)

{for(std::list::iterator it=L.begin();it!=L.end();it++)

{if(*it==x)

{

L.push_front(x);

L.erase(it);return;

}

}

std::cout<

L.pop_back();

L.push_front(x);

}

intmain()

{

std::listL;intsum, n, i,x;

sum= 0; //初始cache内没有数据

std::cin>>n; //读入页数

while (true)

{

scanf("%d", &x);if (x < 0)

{break;

}else{if (sum < n) //cache未满,放至后面

{

L.push_front(x);

std::cout<

sum += 1; //并对cache+1

}else{

fun(L,x);

}

}

}return 0;

}

C++ list 因为内部就是双向链表

public classLRUCache{private intlimit;private HashMaphashMap;privateNode head;privateNode end;public LRUCache(intlimit)

{this.limit =limit;

hashMap= new HashMap();

}publicString get(String key){

Node node=hashMap.get(key);if(node ==null)return null;

refreshNode(node);returnnode.value;

}public voidput(String key,String value){

Node node=hashMap.get(key);if(node == null){if(hashMap.size()>=limit)

{

String oldKey=removeNode(head);

hashMap.remove(oldKey);

}

node= newNode(key,value);

addNode(node);

hashMap.put(key,node)

}else{

node.value=value;

refreshNode(node);

}

}public voidremove(String key){

Node node=hashMap.get(key);

removeNode(node);

hashMap.remove(key);

}private voidrefreshNode(Node node)

{if(node ==end)return;

removeNode(node);

addNode(node);

}publicString removeNode(Node node){if(node ==end)

end=end.pre;else if(node ==head)

head=head.next;else{

node.pre.next=node.next;

node.next.pre=node.pre;

}returnnode.key;

}public voidaddNode(Node node)

{if(end!=null)

{

end.next=node;

node.pre=end;

node.next= null;

}

end=node;if(head == null)

head=node;

}

}

Java实现(高并发线程安全使用ConcurrentHashMap

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。