LRU置换算法 ---页面置换算法中使用策略模式

来源:互联网 发布:网络兼职宣传语 编辑:程序博客网 时间:2024/05/18 02:32
LRU是Least Recently Used 近期最少使用算法。
内存管理的一种页面置换算法,对于在内存中但又不用的数据块(内存块)叫做LRU,Oracle会根据哪些数据属于LRU而将其移出内存而腾出空间来加载另外的数据。
什么是LRU算法? LRU是Least Recently Used的缩写,即最少使用页面置换算法,是为虚拟页式存储管理服务的。
关于操作系统的内存管理,如何节省利用容量不大的内存为最多的进程提供资源,一直是研究的重要方向。而内存的虚拟存储管理,是现在最通用,最成功的方式—— 在内存有限的情况下,扩展一部分外存作为虚拟内存,真正的内存只存储当前运行时所用得到信息。这无疑极大地扩充了内存的功能,极大地提高了计算机的并发度。虚拟页式存储管理,则是将进程所需空间划分为多个页面,内存中只存放当前所需页面,其余页面放入外存的管理方式。
然而,有利就有弊,虚拟页式存储管理减少了进程所需的内存空间,却也带来了运行时间变长这一缺点:进程运行过程中,不可避免地要把在外存中存放的一些信息和内存中已有的进行交换,由于外存的低速,这一步骤所花费的时间不可忽略。因而,采取尽量好的算法以减少读取外存的次数,也是相当有意义的事情。
策略模式定义了一系列的算法,并将每一个算法封装起来,而且使它们还可以相互替换。策略模式让算法独立于使用它的客户而独立变化—抽象策略角色: 策略类,通常由一个接口或者抽象类实现。

1组成编辑

—具体策略角色:包装了相关的算法和行为。
—环境角色:持有一个策略类的引用,最终给客户端调用。


public abstract class Swapping {

protected Memory memory;


public Memory getMemory() {
return memory;
}
//返回值是-1表示该页面已经在内存里了
//[0,Memory.memorySize)表示要把他装入那个位置
public abstract int getLoacalLoadPage(Integer chunk);


public void setMemory(Memory memory) {
this.memory = memory;
}
}
import java.util.Stack;




public class LRUSwapping extends Swapping{

private Stack<Integer> stack=new Stack<Integer>();


@Override
public int getLoacalLoadPage(Integer chunk) {

if(memory.getUsedMemoryCount()<Memory.memorySize){
boolean flag=stack.remove(chunk);
stack.push(chunk);
return flag?-1:memory.getUsedMemoryCount();
}else{
boolean flag=stack.remove(chunk);
stack.push(chunk);
if(flag){
return -1;
}else{
Integer chunk1=stack.get(0);//栈底页面
//System.out.println("stack----->>>"+chunk1);
stack.remove(chunk1);
// System.out.println("stack----->>>"+chunk1);
// System.out.println("memory.getIndexOfExistedChunk(chunk1)--->>>"+memory.getIndexOfExistedChunk(chunk1));
return memory.getIndexOfExistedChunk(chunk1);
}
}
}
}
import java.util.ArrayList;
import java.util.List;


public class Memory {


public static final int memorySize = 4;// 内存是四个物理块
private List<Integer> list = new ArrayList<Integer>(memorySize);
private Swapping swapping;


public Memory(Swapping swapping) {
super();
this.swapping = swapping;
this.swapping.setMemory(this);
}


// -2表示内存还没满
// -1表示原来的页面本来就在内存里
// >0表示将几号页面换出了
public int loadPage(Integer chunk) {
int index = swapping.getLoacalLoadPage(chunk);


// System.out.println("index--->>>"+index);
Integer chunk1 = null;


try {
chunk1 = list.get(index);
} catch (Exception e) {
}
this.load(chunk, index);


if (getUsedMemoryCount() <= Memory.memorySize) {
if (getUsedMemoryCount() == Memory.memorySize && index == -1) {
return -1;
}
return -2;
} else {
// System.out.println("index--->>>"+index);
/*
* if(index==-1){

* }
*/


// System.out.println("chunk1--->>>"+chunk1);
list.remove(chunk1);
return chunk1;
}


}


public int getIndexOfExistedChunk(Integer chunk) {


return list.indexOf(chunk);


}


public int getUsedMemoryCount() {
return list.size();
}


public void load(int chunk, int index) {
if (index >= 0) {
list.add(index, chunk);
}
}
/*
* public static void main(String[] args) { Swapping swapping=new
* LRUSwapping(); Memory memory=new Memory(swapping);
* System.out.println(memory.loadPage(4));
* System.out.println(memory.loadPage(3));
* System.out.println(memory.loadPage(2));
* System.out.println(memory.loadPage(1));
* System.out.println(memory.loadPage(5)); }
*/


}


public class Main {

public static void main(String[] args) {
int QString[] = { 7, 0, 1, 2, 0, 3, 0, 4, 2, 3, 0, 3, 2, 1, 2, 0, 1, 7,
0, 1 };
Swapping swapping=new LRUSwapping();
    Memory memory=new Memory(swapping);
for(Integer chunk:QString){
int result=memory.loadPage(chunk);

switch (result) {
case -2:
System.out.println(chunk+"号页面加载进内存..........");
break;
case -1:
System.out.println(chunk+"号页面已经在内存了..........");
break;


default:
System.out.println(chunk+"号页面把"+result+"号页面置换出内存..........");
break;
}

}
}


}

0 0
原创粉丝点击