# 进程调度(FCFS和SJF)
## 问题描述
设计程序模拟进程的先来先服务FCFS和短作业优先SJF调度过程。假设有n个进程分别在T1, … ,Tn时刻到达系统,它们需要的服务时间分别为S1, … ,Sn。分别采用先来先服务FCFS和短作业优先SJF进程调度算法进行调度,计算每个进程的完成时间,周转时间、带权周转时间和等待时间,并且统计n个进程的平均周转时间、平均带权周转时间和平均等待时间。最后,对两个算法做出比较评价。
要求采用先来先服务FCFS和短作业优先SJF分别调度进程运行,计算每个进程的周转时间,带权周转时间和等待时间,并且计算所有进程的平均周转时间,带权平均周转时间和平均等待时间。
## 实验环境
- Windows 11
- Visual Studio Code
- gcc version 8.1.0
## 输入
进程数n,进程编号,以及每个进程的到达时间T1, … ,Tn和服务时间S1, … ,Sn。在屏幕上要以表的形式显示输入的信息。
根据显示信息:“1-FCFS,2-SJF”,选择1或者2进入对应的算法过程。
## 输出
- 要求模拟整个调度过程,输出每个时刻的进程运行状态
- 要求输出计算出来的每个进程的周转时间,带权周转时间和等待时间
- 要求输出所有进程的平均周转时间,带权平均周转时间和平均等待时间
## 测试数据
| **Process Num.** | **1** | **2** | **3** | **4** | **5** |
| ---------------- | ----- | ----- | ----- | ----- | ----- |
| **Arrival Time** | **0** | **1** | **3** | **4** | **6** |
| **CPU Burst** | **5** | **7** | **3** | **8** | **2** |
## 实验设计
### 数据结构
```cpp
#define MaxNum 100 // 最大进程数
double AverageWT_FCFS = 0, AverageWT_SJF = 0; // 平均等待时间
double AverageTAT_FCFS = 0, AverageTAT_SJF = 0; // 平均周转时间
double AverageWTAT_FCFS = 0, AverageWTAT_SJF = 0; // 平均带权周转时间
using namespace std;
// 进程结构体
typedef struct PROCESS
{
int index; // 进程序号
double ServiceTime; // 服务时间
double ArrivalTime; // 到达时间
double StartTime; // 开始时间
double FinishTime; // 结束时间
double TurnArroundTime; // 周转时间
double WaitTime; // 等待时间
double WeightTurnArroundTime; // 带权周转时间
} PRO[MaxNum];
```
### 函数的功能、参数和输出
```cpp
// 输出各进程的到达时间和服务时间
void display_base(PRO PC, int n)
// 输出每个时刻的进程运行状态
void display_status(PRO PC, int n)
// 输出各进程的周转时间、带权周转时间和等待时间
void display_time(PRO PC, int n)
// 输出所有进程的的平均周转时间、带权平均周转时间和平均等待时间
void display_average()
// 按到达时间排序
void SortArrival(PRO &PC, int n)
// 计算各项时间 z为记号变量 用于区别FCFS和SJF
void CountTime(PRO &PC, int n, int z)
// FCFS算法
void FCFS(PRO &PC, int n)
// SJF算法
void SJF(PRO &PC, int n)
// 关于以上函数的参数,PC均为进程的结构体数组,n均为进程的数量
```
### 主要函数算法设计
```cpp
// 模拟整个调度过程,输出每个时刻的进程运行状态
void display_status(PRO PC, int n)
{
cout << endl;
cout << "Process Num\t"
<< "Start Time\t"
<< "End Time\t"
<< "Ready Queue" << endl;
for (int t = 0; t < n; t++) // 循环输出每个进程的服务时间内 处在等待队列的进程 即到达时间在当前进程开始和结束时间之间的进程
{
cout << PC[t].index << "\t\t" << PC[t].StartTime << "\t\t" << PC[t].FinishTime << "\t\t";
for (int q = t + 1; q < n; q++)
{
if (PC[q].ArrivalTime <= PC[t].FinishTime)
cout << PC[q].index << " ";
}
cout << endl;
}
}
```
```cpp
// 按到达时间排序
void SortArrival(PRO &PC, int n)
{
PROCESS temp;
for (int i = 0; i < n; i++)
{
int min = i;
for (int j = i + 1; j < n; j++)
if (PC[j].ArrivalTime < PC[min].ArrivalTime)
min = j;
temp = PC[i];
PC[i] = PC[min];
PC[min] = temp;
}
}
```
```cpp
// 计算各项时间 z为记号变量 用于区别FCFS和SJF
void CountTime(PRO &PC, int n, int z)
{
PC[0].StartTime = PC[0].ArrivalTime;
PC[0].FinishTime = PC[0].ArrivalTime + PC[0].ServiceTime;
PC[0].TurnArroundTime = PC[0].FinishTime - PC[0].ArrivalTime;
PC[0].WaitTime = 0;
PC[0].WeightTurnArroundTime = PC[0].TurnArroundTime / PC[0].ServiceTime;
double sumWT = PC[0].WaitTime, sumTAT = PC[0].TurnArroundTime, sumWTAT = PC[0].WeightTurnArroundTime;
for (int m = 1; m < n; m++)
{
if (PC[m].ArrivalTime >= PC[m - 1].FinishTime)
{
PC[m].StartTime = PC[m].ArrivalTime;
PC[m].WaitTime = 0;
}
else
{
PC[m].StartTime = PC[m - 1].FinishTime;
PC[m].WaitTime = PC[m - 1].FinishTime - PC[m].ArrivalTime;
}
PC[m].FinishTime = PC[m].StartTime + PC[m].ServiceTime;
PC[m].TurnArroundTime = PC[m].FinishTime - PC[m].ArrivalTime;
PC[m].WeightTurnArroundTime = PC[m].TurnArroundTime / PC[m].ServiceTime;
sumWT += PC[m].WaitTime;
sumTAT += PC[m].TurnArroundTime;
sumWTAT += PC[m].WeightTurnArroundTime;
}
if(z == 1) // 计算FCFS
{
AverageWT_FCFS = sumWT / n;
AverageTAT_FCFS = sumTAT / n;
AverageWTAT_FCFS = sumWTAT / n;
}
if(z == 2) // 计算SJF
{
AverageWT_SJF = sumWT / n;
AverageTAT_SJF = sumTAT / n;
AverageWTAT_SJF = sumWTAT / n;
}
}
```
```cpp
// FCFS算法
void FCFS(PRO &PC, int n)
{
SortArrival(PC, n); // 按到达时间进行排序
CountTime(PC, n, 1); // 计算各项时间
display_status(PC, n); // 模拟整个调度过程,输出每个时刻的进程运行状态
display_time(PC, n); // 输出各进程的周转时间、带权周转时间和等待时间
}
```
```cpp
// SJF算法
void SJF(PRO &PC, int n)
{
SortArrival(PC, n); // 先按到达时间进行排序
// 类比选择排序的思想 从第二个到达的进程开始 遍历当前进程后面的进程 如果有服务时间比当前最短服务时间更短的 则交换位置
int End = PC[0].ArrivalTime + PC[0].ServiceTime; // 之前服务的结束时间
int tmin = 1; // 当前最短服务时间的索引
PROCESS temp;
for (int x = 1; x < n; x++)
{
for (int y = x + 1; y < n; y++)
{
if (PC[y].ArrivalTime <= End && PC[y].ServiceTime < PC[tmin].ServiceTime)
tmin = y;
}
// 将当前进程与等待队列中服务时间最短的进程进行交换
temp = PC[x];
PC[x] = PC[tmin];
PC[tmin] = temp;
End += PC[x].ServiceTime;
}
CountTime(PC, n, 2); // 计算各项时间
display_status(PC, n); // 模拟整个调度过程,输出每个时刻的进程运行状态
display_time(PC, n); // 输出各进程的周转时间、带权周转时间和等待时间
}
```
### 详细设计
- 变量初始化
- 接收用户输入n,T1, … ,Tn,S1, … ,Sn
- 循环等待用户选择算法:1-FCFS,2-SJF
- 按照选择算法进行进程调度
- 计算进程的开始时间、完成时间、周转时间、带权周转时间和等待时间
- 计算所有进程的平均周转时间、平均带权周转时间和平均等待时间
- 按格式输出调度结果
### 流程图
![](https://s2.loli.net/2022/03/24/mIsGlcp12eyw5gM.png)
## 实验结果与分析
### 结果展示与描述
![](https://s2.loli.net/2022/03/24/AIXwD2H3CMZvpmK.png)
- 输入进程数量和各进程的基本信息:到达时间和服务时间
- �
程序员张小妍
- 粉丝: 1w+
- 资源: 3474
最新资源
- 员工培训需求调查问卷.doc
- 如何确定针对性的培训需求.doc
- 素质能力培训需求分析模型.doc
- 怎样进行有效的培训需求分析(doc 9).doc
- 制造业各工位培训需求.doc
- 做好培训需求分析,奠定企业员工培训的基础(DOC 8页).doc
- SQLSERVER2005卸载方法word文档doc格式最新版本
- MicrosoftSQLServer2008安装和数据库实例创建操作手册doc版冯冰最新版本
- 西电微机原理实验PDF
- P6ProfessionalSetup R24.12 安装包
- MicrosoftSQLServer2008数据库安装图解集合[特别整理版]最新版本
- 含光伏的储能选址定容模型 14节点 程序采用改进粒子群算法,对分析14节点配网系统中的储能选址定容方案,并得到储能的出力情况,有相关参考资料 这段程序是一个粒子群算法(Particle Swarm O
- PROGPPCNEXUS读写烧录刷写软件 飞思卡尔MPC55xx 56xx 57xx 58xx 没有次数限制
- 01_python_基本语法_纯图版.pdf
- 考虑新能源消纳的火电机组深度调峰策略 摘要:本代码主要做的是考虑新能源消纳的火电机组深度调峰策略,以常规调峰、不投油深度调峰、投油深度调峰三个阶段,建立了火电机组深度调峰成本模型,并以风电全额消纳为前
- EV3100电梯专用变频器源代码
资源上传下载、课程学习等过程中有任何疑问或建议,欢迎提出宝贵意见哦~我们会及时处理!
点击此处反馈
- 1
- 2
- 3
前往页