/// <summary> /// Reads a file containing processes to be executed and converts it to a list of processes /// </summary> /// <returns>a list of processes with two properties given in the file</returns> public List<ProcessElement> GetData() { string[] lines = File.ReadAllLines(FILENAME); string[] fields; string input; List<ProcessElement> processList = new List<ProcessElement> { }; foreach (string line in lines) // parse each line in file { try { if (line != "" && !line.StartsWith("#")) // empty lines and comments are ignored { ProcessElement process = new ProcessElement(); input = line.Trim(); input = Regex.Replace(input, @"\s+", " "); fields = input.Split(' '); process.ArriveTime = Convert.ToInt32(fields[0]); // the first number is the arrival time process.ExeTime = Convert.ToInt32(fields[1]); // the second number is the service time processList.Add(process); } } catch (FormatException e) { Console.WriteLine("Format error: " + e.Message); } } return processList; }
/// <summary> /// The method implements the shorted remain time scheduling algorithm. A process is preempted when /// the newly arrived process has shorter remaining service time. When a process is finished, the /// processor then chooses the next process with the shortest remaining time /// </summary> /// <param name="processList">a list of processes to be executed</param> public void SRT_Schedule(List<ProcessElement> processList) { int totalWaitTime = 0; // keeps track of the total wait time of all jobs int totalTurnAroundTime = 0; // keeps track of he total turnaround time of all jobs double avgWaitTime = 0; // average wait time of all jobs double avgTurnAroundTime = 0; // average turnaround time of all jobs double wTDeviation = 0; // wait time standard deviation double taTDeviation = 0; // turnaround time standard deviation double sumOfWTSquares = 0; // temp values to use in calculating double sumOfTATSquares = 0; // the standard deviations int numOfJobs = processList.Count; // stores the number of job in the list int count = 0; // keeps track of how many processes have been completed int timer = 0; // keeps track of time ProcessElement current = new ProcessElement(); // process currently being ProcessElement next = new ProcessElement(); // the next process in the ready queue List<ProcessElement> waitlist = new List<ProcessElement> { }; // if there is no process, exit the method if (processList.Count == 0) { logger.Log("There are no processes to be executed."); return; } // while there are incomplete processes while (count < processList.Count-1) { // get a sublist of processes that have arrived and uncompleted List<ProcessElement> sublist = processList.Where(p => (p.RemainTime > 0 && p.ArriveTime <= timer)).ToList(); // if sublist is not empty if (sublist.Count != 0) { current = sublist.First(); // set the first element to be the current process // go through each process in the sublist foreach (ProcessElement p in sublist) { // and find the process with the shorted remaining time if (p.RemainTime < current.RemainTime) { current = p; // set that to be the next process executed if (current.RemainTime == current.ExeTime) current.WaitTime = timer - current.ArriveTime; } } current.RemainTime--; // execute the process timer++; // update the timer current.TurnAroundTime = timer - current.ArriveTime; // update the turnaround time if (current.RemainTime == 0) // if the process is finished { count++; // increment the count value processList.ElementAt(current.JobNumber - 1).TurnAroundTime = current.TurnAroundTime; // copy the turnaround time to the process list } } else { while (processList.ElementAt(count).ArriveTime > timer && count!=processList.Count-1) timer++; // if no sublist is generated, increment the timer while waiting for a new process to arrive } } //logging data in file logger.Log("Shortest Remaining Time Algorithm\n"); logger.DisableFileLogging(); logger.Log("Data has been logged to file SRT.csv\n\n"); logger.DisableConsoleLogging(); logger.EnableFileLogging(); logger.Log("Arrival Time,Wait Time,Turnaround Time,\n"); try { foreach (ProcessElement p in processList) { //p.WaitTime = p.TurnAroundTime - p.ExeTime; // wait time is equal to the difference between the turnaround time and execution time logger.Log(p.ArriveTime.ToString() + "," + p.WaitTime.ToString() + "," + p.TurnAroundTime + ",\n"); totalWaitTime += p.WaitTime; totalTurnAroundTime += p.TurnAroundTime; } // standard deviation = the square root of (the (the sum of the square of the difference between each item and the mean)/number of elements) avgWaitTime = (double)totalWaitTime / (double)numOfJobs; // calculate average wait time avgTurnAroundTime = (double)totalTurnAroundTime / (double)numOfJobs; // calculate average turnaround time foreach (ProcessElement p in processList) { sumOfWTSquares += Math.Pow(p.WaitTime - avgWaitTime, 2); sumOfTATSquares += Math.Pow(p.TurnAroundTime - avgTurnAroundTime, 2); } wTDeviation = Math.Sqrt(sumOfWTSquares / count); taTDeviation = Math.Sqrt(sumOfTATSquares / count); logger.Log("\n\nAvg WaitTime,Avg TurnaroundTime,Std Dev of WaitTime, Std Dev of TurnaroundTime,\n"); logger.Log(avgWaitTime.ToString("f2") + "," + avgTurnAroundTime.ToString("f2") + "," + wTDeviation.ToString("f2") + "," + taTDeviation.ToString("f2") + ",\n"); } catch (DivideByZeroException de) { logger.EnableConsoleLogging(); logger.Log(de.Message); } }
// a method that schedules processes based on the order of their entries. // accept a process list // return nothing public void FCFS_Schedule(List<ProcessElement> processList) { int totalWaitTime = 0; // keeps track of the total wait time of all jobs int totalTurnAroundTime = 0; // keeps track of he total turnaround time of all jobs double avgWaitTime = 0; // average wait time of all jobs double avgTurnAroundTime = 0; // average turnaround time of all jobs double wTDeviation = 0; // wait time standard deviation double taTDeviation = 0; // turnaround time standard deviation double sumOfWTSquares = 0; // temp values to use in calculating double sumOfTATSquares = 0; // the standard deviations int numOfJobs = processList.Count; // stores the number of job in the list int count = 0; // index variable int timer = 0; // a variable to keep track of time if (processList.Count == 0) { logger.Log("There are no processes to be executed."); return; } // for each element in processList, calculate its data while (count < processList.Count) { process = processList.ElementAt(count); // each of the element in the list while (timer < process.ArriveTime) // if the process has not yet arrive, wait till it arrives timer++; timer += process.ExeTime; // update the timer after the execution of the process process.TurnAroundTime = timer - process.ArriveTime; // each process's turnaround time equals exe time + wait time count++; // increment the index variable to get the next process } // logging data to file logger.Log("First Come First Served Algorithm\n"); logger.DisableFileLogging(); logger.Log("Data has been logged to file RoundRobin.csv\n\n"); logger.DisableConsoleLogging(); logger.EnableFileLogging(); logger.Log("Arrival Time,Wait Time,Turnaround Time,\n"); try { foreach (ProcessElement p in processList) { p.WaitTime = p.TurnAroundTime - p.ExeTime; // wait time is equal to the difference between the turnaround time and execution time logger.Log(p.ArriveTime.ToString() + "," + p.WaitTime.ToString() + "," + p.TurnAroundTime + ",\n"); totalWaitTime += p.WaitTime; totalTurnAroundTime += p.TurnAroundTime; } // standard deviation = the square root of (the (the sum of the square of the difference between each item and the mean)/number of elements) avgWaitTime = (double)totalWaitTime / (double)numOfJobs; // calculate average wait time avgTurnAroundTime = (double)totalTurnAroundTime / (double)numOfJobs; // calculate average turnaround time foreach (ProcessElement p in processList) { sumOfWTSquares += Math.Pow(p.WaitTime - avgWaitTime, 2); sumOfTATSquares += Math.Pow(p.TurnAroundTime - avgTurnAroundTime, 2); } wTDeviation = Math.Sqrt(sumOfWTSquares / count); taTDeviation = Math.Sqrt(sumOfTATSquares / count); logger.Log("\n\nAvg WaitTime,Avg TurnaroundTime,Std Dev of WaitTime, Std Dev of TurnaroundTime,\n"); logger.Log(avgWaitTime.ToString("f2") + "," + avgTurnAroundTime.ToString("f2") + "," + wTDeviation.ToString("f2") + "," + taTDeviation.ToString("f2") + ",\n"); } // catch any error caused by dividing 0 catch (DivideByZeroException de) { logger.EnableConsoleLogging(); logger.Log(de.Message); } }
/// <summary> /// This method is an implementation of the shorted process next scheduling algorithm. /// It executes the ready process with the shorted processing time first without preempting it. /// </summary> /// <param name="processList">A list of processes to be executed</param> public void SPN_Schedule(List<ProcessElement> processList) { int totalWaitTime = 0; // keeps track of the total wait time of all jobs int totalTurnAroundTime = 0; // keeps track of he total turnaround time of all jobs double avgWaitTime = 0; // average wait time of all jobs double avgTurnAroundTime = 0; // average turnaround time of all jobs double wTDeviation = 0; // wait time standard deviation double taTDeviation = 0; // turnaround time standard deviation double sumOfWTSquares = 0; // temp values to use in calculating double sumOfTATSquares = 0; // the standard deviations int numOfJobs = processList.Count; // stores the number of job in the list int count = 0; // keeps track of how many processes have been executed int timer = 0; // keeps track of time int minExeTime = 0; // stores the shorted processing time ProcessElement current = new ProcessElement(); // process currently being executed // if there is no process, exit the method if (processList.Count == 0) { logger.Log("There are no processes to be executed."); return; } current = processList.First(); // otherwise, set the first process in the list to current // if current process has not arrived yet, increment the timer until it arrives. while (current.ArriveTime > timer) timer++; // while there are still processes in the process list while (count < processList.Count-1) { // if current process is incomplete if (current.RemainTime != 0) { count++; // increment the count value timer += current.ExeTime; // update the timer current.RemainTime -= current.ExeTime; // execute the program current.TurnAroundTime = timer - current.ArriveTime; // update its turnaround time processList.ElementAt(current.JobNumber - 1).TurnAroundTime = current.TurnAroundTime; //copy the TAT info back into the processList } // query for a sublist that contains the ready processes that are to be executed List<ProcessElement> sublist = processList.Where(p => (p.RemainTime > 0 && p.ArriveTime <= timer)).ToList(); // if sublist is not empty if (sublist.Count != 0) { minExeTime = sublist.First().ExeTime; // set the minimum service time to the first element in the sublist current = sublist.First(); // set current process to the first element in the sublist // go through each process in the sublist for (int i = 0; i < sublist.Count; i++) { // find the process with the shortest processing time and set that to the next process to be executed if (minExeTime > sublist.ElementAt(i).ExeTime) { minExeTime = sublist.ElementAt(i).ExeTime; current = sublist.ElementAt(i); } } } else // if no sublist is found, increment the timer until a new process arrives { while (processList.ElementAt(count).ArriveTime > timer) timer++; } } //logging data in file logger.Log("Shortest Process Next Algorithm\n"); logger.DisableFileLogging(); logger.Log("Data has been logged to file SPN.csv\n\n"); logger.DisableConsoleLogging(); logger.EnableFileLogging(); logger.Log("Arrival Time,Wait Time,Turnaround Time,\n"); try { foreach (ProcessElement p in processList) { p.WaitTime = p.TurnAroundTime - p.ExeTime; // wait time is equal to the difference between the turnaround time and execution time logger.Log(p.ArriveTime.ToString() + "," + p.WaitTime.ToString() + "," + p.TurnAroundTime + ",\n"); totalWaitTime += p.WaitTime; totalTurnAroundTime += p.TurnAroundTime; } // standard deviation = the square root of (the (the sum of the square of the difference between each item and the mean)/number of elements) avgWaitTime = (double)totalWaitTime / (double)numOfJobs; // calculate average wait time avgTurnAroundTime = (double)totalTurnAroundTime / (double)numOfJobs; // calculate average turnaround time foreach (ProcessElement p in processList) { sumOfWTSquares += Math.Pow(p.WaitTime - avgWaitTime, 2); sumOfTATSquares += Math.Pow(p.TurnAroundTime - avgTurnAroundTime, 2); } wTDeviation = Math.Sqrt(sumOfWTSquares / count); taTDeviation = Math.Sqrt(sumOfTATSquares / count); logger.Log("\n\nAvg WaitTime,Avg TurnaroundTime,Std Dev of WaitTime, Std Dev of TurnaroundTime,\n"); logger.Log(avgWaitTime.ToString("f2") + "," + avgTurnAroundTime.ToString("f2") + "," + wTDeviation.ToString("f2") + "," + taTDeviation.ToString("f2") + ",\n"); } catch (DivideByZeroException de) { logger.EnableConsoleLogging(); logger.Log(de.Message); } }
ProcessElement process = new ProcessElement(); // instantiate a ProcessElement #endregion Fields #region Methods /// <summary> /// This method implements the round robin scheduling technique. Each process is given a quantum /// to execute and is put into a ready stack when a new process arrives /// </summary> /// <param name="processList">List of processes to be executed</param> public void RoundRobin_Schedule(List<ProcessElement> processList) { Queue<ProcessElement> readyQueue = new Queue<ProcessElement> { };// a list of processes preempted ProcessElement current = new ProcessElement(); // process currently being executed ProcessElement next = new ProcessElement(); // the next process in the ready queue const int QUANTUM = 4; // time slice given each process to execute being preempted int numOfJobs = processList.Count; // number of jobs in the ready queue int count = 0; // an index to refer to the job in the list int timer = 0; // keeps track of time int timeAllocated = 0; // time allocated for each process int totalWaitTime = 0; // keeps track of the total wait time of all jobs int totalTurnAroundTime = 0; // keeps track of he total turnaround time of all jobs double avgWaitTime = 0; // average wait time of all jobs double avgTurnAroundTime = 0; // average turnaround time of all jobs double wTDeviation = 0; // wait time standard deviation double taTDeviation = 0; // turnaround time standard deviation double sumOfWTSquares = 0; // temp values to use in calculating double sumOfTATSquares = 0; // the standard deviations // initially, each process's remaining time is its service time foreach (ProcessElement p in processList) p.RemainTime = p.ExeTime; current = processList.ElementAt(count); // set the first job to be the current executing job // if there are jobs in the processList if (processList.Count != 0) // put the first job in the readyQueue readyQueue.Enqueue(processList.First()); else // otherwise program terminates { logger.Log("There are no processes to be executed."); return; } // when there are still processes in the ready queue while (current.ArriveTime > timer) // if the first process has not arrived, increment the timer timer++; // until it arrives while (readyQueue.Count != 0) { // if the process has not arrived yet, wait until it arrives current = readyQueue.Dequeue(); // select the first process in the queue to execute if (current.ExeTime == current.RemainTime) processList.ElementAt(current.JobNumber - 1).WaitTime = timer - current.ArriveTime; // when a process arrives and it has not finished executing if (current.RemainTime > 0 && current.RemainTime <= QUANTUM) { timeAllocated = current.RemainTime; // time allocated is its remain time current.RemainTime -= timeAllocated; // execute the job } else { timeAllocated = QUANTUM; // otherwise, time allocated is the quantum specified current.RemainTime -= timeAllocated; // execute the job } timer += timeAllocated; // update the timer timeAllocated = 0; //reset the time that's been allocated current.TurnAroundTime = timer - current.ArriveTime; // update current process's turnaround time // if there are other incomplete processes in the ready queue, update their TAT if (readyQueue.Count != 0) { foreach (ProcessElement p in readyQueue) { if (p.RemainTime != 0) p.TurnAroundTime = timer - p.ArriveTime; } } // if the current process is completed, copy its TAT to the process list if (current.RemainTime == 0) { processList.ElementAt(current.JobNumber - 1).TurnAroundTime = current.TurnAroundTime; } // when there are still processes expected, go through each expected process // and find the processes that have arrived for (int i = count; i < numOfJobs; ++i) { if (count < numOfJobs - 1) { count++; // increment the count value next = processList.ElementAt(count); // set next to the next process in the list // if the job arrives and its remain time is not 0 if (timer >= next.ArriveTime && next.RemainTime != 0) { readyQueue.Enqueue(next); // add it to the ready queue } else count--; // otherwise, restore the count value if (next.ExeTime == 0) // if the process does not take any time to execute, move on count++; } } // if current process is not finished, add it back to the ready queue if (current.RemainTime != 0) readyQueue.Enqueue(current); } //logging data in file logger.Log("Round-Robin Algorithm\n"); logger.DisableFileLogging(); logger.Log("Data has been logged to file RoundRobin.csv\n\n"); logger.DisableConsoleLogging(); logger.EnableFileLogging(); logger.Log("Arrival Time,Wait Time,Turnaround Time,\n"); try { foreach (ProcessElement p in processList) { //p.WaitTime = p.TurnAroundTime - p.ExeTime; // wait time is equal to the difference between the turnaround time and execution time logger.Log(p.ArriveTime.ToString() + "," + p.WaitTime.ToString() + "," + p.TurnAroundTime + ",\n"); totalWaitTime += p.WaitTime; totalTurnAroundTime += p.TurnAroundTime; } // standard deviation = the square root of (the (the sum of the square of the difference between each item and the mean)/number of elements) avgWaitTime = (double)totalWaitTime / (double)numOfJobs; // calculate average wait time avgTurnAroundTime = (double)totalTurnAroundTime / (double)numOfJobs; // calculate average turnaround time foreach (ProcessElement p in processList) { sumOfWTSquares += Math.Pow(p.WaitTime - avgWaitTime, 2); sumOfTATSquares += Math.Pow(p.TurnAroundTime - avgTurnAroundTime, 2); } wTDeviation = Math.Sqrt(sumOfWTSquares / count); taTDeviation = Math.Sqrt(sumOfTATSquares / count); logger.Log("\n\nAvg WaitTime,Avg TurnaroundTime,Std Dev of WaitTime, Std Dev of TurnaroundTime,\n"); logger.Log(avgWaitTime.ToString("f2") + "," + avgTurnAroundTime.ToString("f2") + "," + wTDeviation.ToString("f2") + "," + taTDeviation.ToString("f2") + ",\n"); } catch (DivideByZeroException de) { logger.EnableConsoleLogging(); logger.Log(de.Message); } }