磁碟排程演算法 C++實現
阿新 • • 發佈:2018-12-23
常見的磁碟排程演算法大致分為以下5類:
FCFS、SSTF、SCAN、CSCAN、FSCAN
程式實現了上述5類排程演算法。
其中,當前磁軌和要求服務的磁軌均由系統隨機產生。
程式入口是main主函式,在程式一開始由request()函式產生隨機的要求服務的磁碟序列。然後由使用者選擇演算法FCFS、SSTF、SCAN、CSCAN、FSCAN其中之一。
分別執行相應的演算法。
1)FCFS演算法實現思路:將vector內隨機產生的數依次讀出,相當於對於佇列資料結構中的出隊操作。
2)SSTF演算法實現思路:在時間複雜度和空間複雜度上的綜合考慮,我首先將vector內的資料進行排序,然後確定當前磁軌號在有序資料中的位置,然後在該位置的左右找到離它最近的數,並將當前位置進行重新整理。
3)SCAN演算法實現思路:首先將vector內的資料進行排序,然後同樣地確定當前磁軌號在有序資料中的位置,然後在向內的方向上依次訪問,訪問完了之後,再輸出初始位置向外的服務序列。
4)CSCAN演算法實現思路:開始和前面的演算法一樣,也是先進行排序,定位,然後在向內的方向上依次訪問,訪問完了之後,再從最外層向內掃。
5)FSCAN演算法實現思路:將初始的序列放在一個佇列中,將在掃描過程中新出現的服務序列放在另一個序列中,然後對兩個佇列中的資料依次進行SCAN演算法的實現。
程式流程圖:實驗結果:
源程式:
#include <iostream> #include <time.h> #include <vector> #include <math.h> #include <stdlib.h> #include <algorithm> #include <cstring> #include <windows.h> #include <fstream> using namespace std; int position = 0; //當前磁軌位置 int dis = 0; double average_distance = 0; void request(vector<int>&m_vec,ofstream &outfile){ cout<<"隨機生成磁碟序列:"<<endl; int n = 0; srand(time(NULL)); //新增隨機數種子 n = rand() % 20 + 1; int temp = 0; for(int i=0;i<n;i++){ temp = rand() % 100; m_vec.push_back(temp); cout<<temp<<" "; outfile<<temp<<endl; } cout<<endl; position = rand() % 100; cout<<"當前磁軌:"<<position<<endl; } void compute_dis(vector<int>m_vec,int &dis,double &average_distance){ average_distance = (double)dis / (double)m_vec.size(); } void FIFO(vector<int>m_vec,int position){ //先來先服務演算法 dis = 0; average_distance = 0; for(vector<int>::iterator it=m_vec.begin();it!=m_vec.end();it++){ dis += abs(position-*it); Sleep(500); cout<<"->"<<*it; position = *it; } compute_dis(m_vec,dis,average_distance); } void SSTF(vector<int>m_vec,int position){ //最短尋道時間演算法 dis = 0; average_distance = 0; sort(m_vec.begin(),m_vec.end()); //從小到大排序 int i = 0; for(vector<int>::iterator it=m_vec.begin();it!=m_vec.end();it++){ if(position >= *it) i++; } int count = 0; int left = i-1; int right = i; while(count<m_vec.size()){ if((left >=0 && abs(m_vec[right]-position) > abs(m_vec[left]-position)) || right>=m_vec.size()){ dis += abs(m_vec[left]-position); Sleep(500); cout<<"->"<<m_vec[left]; position = m_vec[left]; left--; } else{ dis += abs(m_vec[right]-position); Sleep(500); cout<<"->"<<m_vec[right]; position = m_vec[right]; right++; } count++; } compute_dis(m_vec,dis,average_distance); } void SCAN(vector<int>m_vec,int position){ //電梯排程演算法 dis = 0; average_distance = 0; sort(m_vec.begin(),m_vec.end()); //從小到大排序 int i = 0; for(vector<int>::iterator it=m_vec.begin();it!=m_vec.end();it++){ if(position >= *it) i++; //找到position所在的磁軌 } int left = i - 1; //先從外到內掃描 int right = i; while(left >= 0){ dis += abs(position - m_vec[left]); Sleep(500); cout<<"->"<<m_vec[left]; position = m_vec[left]; left --; } while(right < m_vec.size()){ dis += abs(position - m_vec[right]); Sleep(500); cout<<"->"<<m_vec[right]; position = m_vec[right]; right ++; } compute_dis(m_vec,dis,average_distance); } void CSCAN(vector<int>m_vec,int position){ //迴圈掃描演算法 dis = 0; average_distance = 0; sort(m_vec.begin(),m_vec.end()); //從小到大排序 int i = 0; for(vector<int>::iterator it=m_vec.begin();it!=m_vec.end();it++){ if(position >= *it) i++; //找到position所在的磁軌 } int left = i - 1; //先從外到內掃描 int right = i; while(left >= 0){ dis += abs(position - m_vec[left]); Sleep(500); cout<<"->"<<m_vec[left]; position = m_vec[left]; left --; } position = 100; //立即到最外側的磁軌 int len = m_vec.size()-1; while(len >= right){ dis += abs(position - m_vec[len]); Sleep(500); cout<<"->"<<m_vec[len]; position = m_vec[len]; len --; } compute_dis(m_vec,dis,average_distance); } void FSCAN(vector<int>m_vec,int position){ //分步電梯排程演算法,。分兩個佇列 dis = 0; average_distance = 0; //SCAN(m_vec,position); sort(m_vec.begin(),m_vec.end()); //從小到大排序 int i = 0; for(vector<int>::iterator it=m_vec.begin();it!=m_vec.end();it++){ if(position >= *it) i++; //找到position所在的磁軌 } int left = i - 1; //先從外到內掃描 int right = i; while(left >= 0){ dis += abs(position - m_vec[left]); Sleep(500); cout<<"->"<<m_vec[left]; position = m_vec[left]; left --; } while(right < m_vec.size()){ dis += abs(position - m_vec[right]); Sleep(500); cout<<"->"<<m_vec[right]; position = m_vec[right]; right ++; } cout<<endl; cout<<"在掃描的過程中新產生的服務序列:"<<endl; vector<int>ve; while(!ve.empty()) ve.pop_back(); int n = 0; n = rand() % 20 + 1; int temp = 0; for(i=0;i<n;i++){ temp = rand() % 100; cout<<temp<<" "; ve.push_back(temp); } cout<<endl; cout<<position; SCAN(ve,position); average_distance = (double)dis / (double)(m_vec.size()+ve.size()); } void print(){ cout<<endl<<endl; cout<<"經計算,磁頭移動的總距離為:"<<dis<<endl; cout<<"磁頭平均移動距離:"<<average_distance<<endl; cout<<endl<<endl; } int choose_algorithm(vector<int>m_vec){ cout<<endl<<endl; cout<<"本實驗可用的排程演算法有以下5種:"<<endl; cout<<"1.FIFO 2.SSTF 3.SCAN 4.CSCAN 5.FSCAN 6.結束本序列的排程 7.結束程式"<<endl; int choice = 0; cout<<"選擇:"<<endl; cin>>choice; cout<<endl; while(choice!=6 && choice!=7){ cout<<"磁碟請求的服務狀況:"<<endl; cout<<position; switch(choice){ case 1: FIFO(m_vec,position);break; case 2: SSTF(m_vec,position);break; case 3: SCAN(m_vec,position);break; case 4: CSCAN(m_vec,position);break; case 5: FSCAN(m_vec,position);break; default: cout<<"******非法輸入!******"<<endl<<endl;break; } if(choice<=7 && choice>=1) print(); cout<<"選擇:"<<endl; cin>>choice; } if(choice == 7) return 0; else cout<<endl<<endl; return 1; } int main(){ cout<<"---------------磁碟排程演算法模擬實驗-----------------"<<endl; ofstream outfile; outfile.open("data.txt"); while(1){ vector<int> vec; while(!vec.empty()) vec.pop_back(); request(vec,outfile); //請求服務序列 int flag = choose_algorithm(vec); if(flag == 0) break; } outfile.close(); return 0; }