赞
踩
要求:
(1)设计一个完整的进程调度系统,至少包含三种常用的算法(FCFS、SPF、静态优先权、响应比、时间片轮转),系统中至少包含5个进程,并且能够体现进程的动态申请;
(2)定义PCB;
(3)结果要能够显示出进程的调度序列及进入系统的时间、运行时间、完成时间、周转时间、带权周转时间、优先权等必要信息;
(4〉设计的输入数据要能体现算法的思想
本人使用Java语言编写,编写过程中在网络中查找大量资料。
本人是本篇代码的唯一作者。
本代码仅限参考学习,禁止抄袭!
先来先服务算法First Come First Service(FCFS):
FCFS的意思是先来先服务(First Come First Service)。
顾名思义就是按照进程被添加到等待队列的先后顺序来进行调用的。
短进程优先算法Short Process First(SPF):SPF的意思是短进程优先(Short Process First),服务时间短的进程在就绪队列前面。
静态优先级调度算法Static Priority-scheduling algorithm(SPSA):系统在调度进程时按优先级从高到低进行调度,在进程运行过程中优先级不再动态地改变。
高响应比优先调度算法Highest Response Ratio Next(HRRN):响应比 =(等待时间+要求服务时间)/ 要求服务时间
为每一个作业引入一个动态优先级,即优先级是可以改变的。
它随等待时间延长而增加,这将使长作业的优先级在等待期间不断地增加,
等到足够的时间后,必然有机会获得处理机。
时间片轮转算法Round Robin(RR):系统把所有就绪进程按先来先服务规则排成一个队列,就绪队列中的所有进程,
可以依次轮流获得一个时间片的处理时间,然后系统又回到队列的开始部分,如此不断循环。
Main:
- package osProject.sjs;
-
- import java.io.*;
- import java.util.*;
-
- public class Main
- {
- static int num;//进程数目
- static PCB[] arr = new PCB[100];
- static PCB[] arrUse = new PCB[100];
- static Scanner sc = new Scanner(System.in);
-
- public static void main(String[] args)
- {
- System.out.println("欢迎进入进程管理系统,请按照提示输入进程信息。");
- Main M = new Main();
- M.inputProcessInf(M);//输入进程,选择输入进程的方式
- M.displayProcessInf();//展示进程初始信息
- //进入菜单选择功能,可以使用多个算法调度进程
- while(true)
- {//此while为了多次选择功能i,在选择退出功能时置flag=1,然后退出
- //本程序使用arrUse而保留arr原数据,为了每次进入不同算法时不存在其他算法的遗留结果数据
- M.copyArray();//将arr中的数据内容拷贝到arrUse中,令算法使用arrUse中未被赋值过的干净数据
- int flag = 0;//用来标记是否需要退出选择算法,置1则退出算法
- M.displayMenu();//展示系统菜单,每执行完一次功能i,再次选择功能时展示一次
- while(true)
- {//为了防止输入i的错误导致无法选择功能,此while直到正确选择功能i时退出,每个if的最后都要有break
- try
- {//在try语句块中书写可能发生异常的代码(选择功能),增强程序健壮性
- int i = sc.nextInt();
- if(i == 1)
- {//选择先来先服务算法FCFS
- executeFCFS();//执行FCFS算法
- break;
- }
- else if(i == 2)
- {//选择短进程优先算法SPF
- executeSPF();//执行SPF算法
- break;
- }
- else if(i == 3)
- {//选择静态优先级调度算法SPSA
- executeSPSA();//执行SPSA算法
- break;
- }
- else if(i == 4)
- {//选择高响应比优先调度算法HRRN
- executeHRRN();//执行HRRN算法
- break;
- }
- else if(i == 5)
- {//时间片轮转算法RR
- executeRR();//执行RR算法
- break;
- }
- else if(i == 6)
- {//选择退出系统
- flag = 1;//flag置1,表示需要退出系统
- break;
- }
- else
- {//输入i不是要求的选项,提示重新选择
- System.out.println("输入有误,请重新输入:");//提示功能i选择的错误
- //输入错误时不需要break,需要重新输入
- }
- }
- catch(Exception e)
- {
- System.out.println("您输入的不是数字,请重新输入!");
- sc = new Scanner(System.in);//这一句要加,否则会进入死循环
- }
- }
- if(flag == 1)
- {//当flag置1时,退出系统
- break;
- }
- }
- sc.close();
- }
-
- private static void executeRR()
- {//执行RR算法
- RR rr = new RR(num, arrUse, sc);//RR算法需要输入时间片大小,所以需要传入Scanner对象
- rr.run();
- System.out.println("请选择是否将本次算法执行结果存入文件?");
- System.out.println("1.是\t 2.否");
- while(true)
- {//while死循环是为了防止输入错误时令用户再次输入,否则输入错误后就跳出了,没法选择存文件
- int x = sc.nextInt();
- if(x == 1 || x == 2)
- {
- if(x == 1) rr.writeFile();//将类数组写入文件
- break;//当选择完文件操作后应该退出本层while
- }
- else
- {
- System.out.println("输入有误,请重新输入:");//提示文件操作的选择错误
- sc = new Scanner(System.in);
- //未选择完文件操纵,不需要退出本层while
- }
- }
- }
-
- private static void executeHRRN()
- {//执行HRRN算法
- HRRN hrrn = new HRRN(num, arrUse);
- hrrn.run();
- System.out.println("请选择是否将本次算法执行结果存入文件?");
- System.out.println("1.是\t 2.否");
- while(true)
- {//while死循环是为了防止输入错误时令用户再次输入,否则输入错误后就跳出了,没法选择存文件
- int x = sc.nextInt();
- if(x == 1 || x == 2)
- {
- if(x == 1) hrrn.writeFile();//将类数组写入文件
- break;//当选择完文件操作后应该退出本层while
- }
- else
- {
- System.out.println("输入有误,请重新输入:");//提示文件操作的选择错误
- sc = new Scanner(System.in);
- //未选择完文件操纵,不需要退出本层while
- }
- }
- }
-
- private static void executeSPSA()
- {//执行SPSA算法
- SPSA spsa = new SPSA(num, arrUse, sc);//SPSA算法要另外输入优先级,需要Scanner变量(也有其他方法)
- spsa.run();
- System.out.println("请选择是否将本次算法执行结果存入文件?");
- System.out.println("1.是\t 2.否");
- while(true)
- {//while死循环是为了防止输入错误时令用户再次输入,否则输入错误后就跳出了,没法选择存文件
- int x = sc.nextInt();
- if(x == 1 || x == 2)
- {
- if(x == 1) spsa.writeFile();//将类数组写入文件
- break;//当选择完文件操作后应该退出本层while
- }
- else
- {
- System.out.println("输入有误,请重新输入:");//提示文件操作的选择错误
- sc = new Scanner(System.in);
- //未选择完文件操纵,不需要退出本层while
- }
- }
- }
-
- private static void executeSPF()
- {//执行SPF算法
- SPF spf = new SPF(num, arrUse);
- spf.run();
- System.out.println("请选择是否将本次算法执行结果存入文件?");
- System.out.println("1.是\t 2.否");
- while(true)
- {//while死循环是为了防止输入错误时令用户再次输入,否则输入错误后就跳出了,没法选择存文件
- int x = sc.nextInt();
- if(x == 1 || x == 2)
- {
- if(x == 1) spf.writeFile();//将类数组写入文件
- break;//当选择完文件操作后应该退出本层while
- }
- else
- {
- System.out.println("输入有误,请重新输入:");//提示文件操作的选择错误
- sc = new Scanner(System.in);
- //未选择完文件操纵,不需要退出本层while
- }
- }
- }
-
- private static void executeFCFS()
- {//执行FCFS算法
- FCFS fcfs = new FCFS(num, arrUse);
- fcfs.run();
- System.out.println("请选择是否将本次算法执行结果存入文件?");
- System.out.println("1.是\t 2.否");
- while(true)
- {//此while为了防止输入错误时令用户再次输入,否则输入错误后就跳出了,
- //没法选择存文件,此while在选择文件操作完成后退出
- int x = sc.nextInt();
- if(x == 1 || x == 2)
- {
- if(x == 1) fcfs.writeFile();//将类数组写入文件
- break;//当选择完文件操作后应该退出本层while
- }
- else
- {
- System.out.println("输入有误,请重新输入:");
- sc = new Scanner(System.in);
- //未选择完文件操纵,不需要退出本层while
- }
- }
- }
-
- private void displayMenu()
- {
- System.out.println("功能菜单:");
- System.out.println("***********************************");
- System.out.println("* 1.先来先服务算法 *");
- System.out.println("* 2.短进程优先算法 *");
- System.out.println("* 3.静态优先级算法 *");
- System.out.println("* 4.高响应比优先调度算法 *");
- System.out.println("* 5.时间片轮转算法 *");
- System.out.println("* 6.退出系统 *");
- System.out.println("***********************************");
- System.out.println("请选择要执行的操作:");
- }
-
- private void copyArray()
- {//将arr中的数据内容拷贝到arrUse中,使用arrUse而保留arr中的原始数据
- //不能使用对象直接赋值,那样它们会引用同一块内容,两者会不独立
- for(int i = 0; i < num; i++)
- {
- arrUse[i] = new PCB();
- arrUse[i].setId(arr[i].getId());
- arrUse[i].setName(arr[i].getName());
- arrUse[i].setArriveTime(arr[i].getArriveTime());
- arrUse[i].setServiceTime(arr[i].getServiceTime());
- arrUse[i].setVisited(0);
- }
- }
-
- private void displayProcessInf()
- {//展示进程未执行算法时的初始信息
- System.out.println("进程初始信息如下:");
- for(int i = 0; i < num; i++)
- {
- //使用式样化输出函数printf()输出信息,使信息便于观看
- //左对齐加"-","8"指域宽为8,占8个字符字符串用"s",整型用"d",浮点类型用"f"
- System.out.printf("%-8s \t%-8s \t%-8s \t%-8s\n",
- "进程id", "进程名", "到达时间", "服务时间");
- System.out.printf("%-8d \t%-8s \t%-8d \t%-8d\n",
- arr[i].getId(), arr[i].getName(), arr[i].getArriveTime(), arr[i].getServiceTime());
- }
- System.out.println();
- }
-
- private void fileReadProcess()
- {//从文件中读入进程信息
- File file = new File("processInf.dat");
- try
- {
- FileInputStream fin = new FileInputStream(file);
- ObjectInputStream in = new ObjectInputStream(fin);
- num = fin.read();
- for(int i = 0; i < num; i++)
- {
- arr[i] = (PCB)in.readObject();
- }
- in.close();
- fin.close();
- }
- catch(Exception e)
- {
- System.out.println("文件\"processInf.dat\"不存在!请重新选择:");
- return;//若文件不存在需要直接return,否则会输出下方“已读入完成”的语句
- }
- System.out.println("文件\"processInf.dat\"中的算法数据已读入完成。");
- System.out.println();
- }
-
- private void fileWriteProcess()
- {//将进程块信息写入文件中
- File file = new File("processInf.dat");
- try
- {
- FileOutputStream fout = new FileOutputStream(file);
- ObjectOutputStream out = new ObjectOutputStream(fout);
- fout.write(num);
- for(int i = 0; i < num; i++)
- {
- out.writeObject(arr[i]);
- }
- out.close();
- fout.close();
- }
- catch(Exception e)
- {
- e.printStackTrace();
- }
- System.out.println("本次算法执行结果已存入文件\"processInf.dat\"中。");
- System.out.println();
- }
-
- private void readProcess()
- {//从控制台手动输入进程信息
- while(true)
- {
- try
- {//在try语句块中书写可能发生异常的代码,增强程序健壮性
- System.out.println("请输入进程数目(2-99):");
- num = sc.nextInt();
- if(num < 2 || num > 99)
- {
- System.out.println("您输入的数字不在要求范围内,请重新输入!");
- }
- else
- {
- System.out.println("进程数目为:" + num);
- System.out.println("请按照提示输入进程相关信息。");
- for(int i = 0; i < num; i++)
- {
- arr[i] = new PCB();
- arr[i].setId(i+1);
- System.out.println("第" + (i+1) + "个进程名:");
- arr[i].setName(sc.next());
- System.out.println("进程到达时间:");
- arr[i].setArriveTime(sc.nextInt());
- System.out.println("进程服务时间:");
- arr[i].setServiceTime(sc.nextInt());
- arr[i].setVisited(0);//置进程i未被执行过
- }
- break;//输入完毕,此处记得要break,否则会死循环
- }
- }
- catch(Exception e)
- {
- System.out.println("您输入的不是数字,请重新输入!");
- sc = new Scanner(System.in);//这一句要加,否则会进入死循环
- }
- }
- System.out.println("进程信息输入完成!");
- }
-
- private void inputProcessInf(Main M)
- {//输入进程,选择输入进程的方式
- System.out.println("请选择输入进程方式:");
- System.out.println("1.手动输入\t 2.文件读入");
- while(true)
- {//为了防止输入x的错误导致无法选择功能,此while直到正确选择功能x时退出,每个if的最后都要有break
- int x = sc.nextInt();
- if(x == 1)
- {
- M.readProcess();//从控制台读入用户输入的进程块信息,读入一次进程信息,可以使用多个算法计算
- System.out.println("是否需要将进程信息保存到文件中?");
- System.out.println("1.是\t 2.否");
- while(true)
- {//此while为了防止输入错误时令用户再次输入
- int y = sc.nextInt();
- if(y == 1 || y == 2)
- {
- if(y == 1) M.fileWriteProcess();//将程序中的进程块信息写入文件中
- break;//当写入操作完成后,退出while循环
- }
- else
- {
- System.out.println("输入有误,请重新输入:");
- sc = new Scanner(System.in);
- //未正确选择操作,不需要退出本层while
- }
- }
- break;
- }
- else if(x == 2)
- {
- M.fileReadProcess();//从文件读入进程块信息
- break;
- }
- else
- {
- System.out.println("输入有误,请重新输入:");
- sc = new Scanner(System.in);
- //else中不用break,因为没有正确选择功能,需要在while中再次输入
- }
- }
- }
-
- }
PCB(进程控制块):
- package osProject.sjs;
-
- import java.io.*;
-
- public class PCB implements Serializable
- {
- /**
- *
- */
- private static final long serialVersionUID = 1L;
-
- private int id;//进程id
- private String name;//进程名称
- private int arriveTime;//进程进入系统的时间(未开始服务),进程到达时间
- private int serviceTime;//进程服务时间,进程服务时间,需提前给出
- private int alreadyServiceTime;//已经服务的时间,进程执行时记录
- private int startTime;//进程服务开始时间
- private int endTime;//进程服务完成时间
- private int turnaroundTime;//周转时间,作业完成时间 - 作业到达时间
- private double turnaroundTimeWithRight;//带权周转时间,周转时间 /服务时间
- private int priority;//优先级
- private double responseRatio;//HRRN中的响应比
- private int visited;//是否被执行过,置0为未被执行过,置1为被执行过
-
- PCB(){}//构造函数
-
- public int getId() {
- return id;
- }
-
- public void setId(int id) {
- this.id = id;
- }
-
- public String getName() {
- return name;
- }
-
- public void setName(String name) {
- this.name = name;
- }
-
- public int getArriveTime() {
- return arriveTime;
- }
-
- public void setArriveTime(int arriveTime) {
- this.arriveTime = arriveTime;
- }
-
- public int getServiceTime() {
- return serviceTime;
- }
-
- public void setServiceTime(int serviceTime) {
- this.serviceTime = serviceTime;
- }
-
- public int getAlreadyServiceTime() {
- return alreadyServiceTime;
- }
-
- public void setAlreadyServiceTime(int alreadyServiceTime) {
- this.alreadyServiceTime = alreadyServiceTime;
- }
-
- public int getStartTime() {
- return startTime;
- }
-
- public void setStartTime(int startTime) {
- this.startTime = startTime;
- }
-
- public int getEndTime() {
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。