Skip to content

Commit da1edad

Browse files
authored
Merge branch 'master' into bipartite_add_tests
2 parents 1776580 + 2001a09 commit da1edad

File tree

4 files changed

+306
-2
lines changed

4 files changed

+306
-2
lines changed

DIRECTORY.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -459,6 +459,7 @@
459459
* [GenerateSubsets](https://github.com/TheAlgorithms/Java/blob/master/src/main/java/com/thealgorithms/Recursion/GenerateSubsets.java)
460460
* scheduling
461461
* [FCFSScheduling](https://github.com/TheAlgorithms/Java/blob/master/src/main/java/com/thealgorithms/scheduling/FCFSScheduling.java)
462+
* [HighestResponseRatioNextScheduling](https://github.com/TheAlgorithms/Java/blob/master/src/main/java/com/thealgorithms/scheduling/HighestResponseRatioNextScheduling.java)
462463
* [MLFQScheduler](https://github.com/TheAlgorithms/Java/blob/master/src/main/java/com/thealgorithms/scheduling/MLFQScheduler.java)
463464
* [PreemptivePriorityScheduling](https://github.com/TheAlgorithms/Java/blob/master/src/main/java/com/thealgorithms/scheduling/PreemptivePriorityScheduling.java)
464465
* [RRScheduling](https://github.com/TheAlgorithms/Java/blob/master/src/main/java/com/thealgorithms/scheduling/RRScheduling.java)
@@ -917,6 +918,7 @@
917918
* [GenerateSubsetsTest](https://github.com/TheAlgorithms/Java/blob/master/src/test/java/com/thealgorithms/Recursion/GenerateSubsetsTest.java)
918919
* scheduling
919920
* [FCFSSchedulingTest](https://github.com/TheAlgorithms/Java/blob/master/src/test/java/com/thealgorithms/scheduling/FCFSSchedulingTest.java)
921+
* [HighestResponseRatioNextSchedulingTest](https://github.com/TheAlgorithms/Java/blob/master/src/test/java/com/thealgorithms/scheduling/HighestResponseRatioNextSchedulingTest.java)
920922
* [MLFQSchedulerTest](https://github.com/TheAlgorithms/Java/blob/master/src/test/java/com/thealgorithms/scheduling/MLFQSchedulerTest.java)
921923
* [PreemptivePrioritySchedulingTest](https://github.com/TheAlgorithms/Java/blob/master/src/test/java/com/thealgorithms/scheduling/PreemptivePrioritySchedulingTest.java)
922924
* [RRSchedulingTest](https://github.com/TheAlgorithms/Java/blob/master/src/test/java/com/thealgorithms/scheduling/RRSchedulingTest.java)

src/main/java/com/thealgorithms/ciphers/a5/CompositeLFSR.java

Lines changed: 34 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,13 +5,33 @@
55
import java.util.Map;
66
import java.util.TreeMap;
77

8+
/**
9+
* The CompositeLFSR class represents a composite implementation of
10+
* Linear Feedback Shift Registers (LFSRs) for cryptographic purposes.
11+
*
12+
* <p>
13+
* This abstract class manages a collection of LFSR instances and
14+
* provides a mechanism for irregular clocking based on the
15+
* majority bit among the registers. It implements the BaseLFSR
16+
* interface, requiring subclasses to define specific LFSR behaviors.
17+
* </p>
18+
*/
819
public abstract class CompositeLFSR implements BaseLFSR {
920

1021
protected final List<LFSR> registers = new ArrayList<>();
1122

1223
/**
13-
* Implements irregular clocking using the clock bit for each register
14-
* @return the registers discarded bit xored value
24+
* Performs a clocking operation on the composite LFSR.
25+
*
26+
* <p>
27+
* This method determines the majority bit across all registers and
28+
* clocks each register based on its clock bit. If a register's
29+
* clock bit matches the majority bit, it is clocked (shifted).
30+
* The method also computes and returns the XOR of the last bits
31+
* of all registers.
32+
* </p>
33+
*
34+
* @return the XOR value of the last bits of all registers.
1535
*/
1636
@Override
1737
public boolean clock() {
@@ -26,6 +46,18 @@ public boolean clock() {
2646
return result;
2747
}
2848

49+
/**
50+
* Calculates the majority bit among all registers.
51+
*
52+
* <p>
53+
* This private method counts the number of true and false clock bits
54+
* across all LFSR registers. It returns true if the count of true
55+
* bits is greater than or equal to the count of false bits; otherwise,
56+
* it returns false.
57+
* </p>
58+
*
59+
* @return true if the majority clock bits are true; false otherwise.
60+
*/
2961
private boolean getMajorityBit() {
3062
Map<Boolean, Integer> bitCount = new TreeMap<>();
3163
bitCount.put(Boolean.FALSE, 0);
Lines changed: 158 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,158 @@
1+
package com.thealgorithms.scheduling;
2+
3+
import java.util.Arrays;
4+
import java.util.Comparator;
5+
6+
/**
7+
* The {@code HighestResponseRatioNextScheduling} class implements the
8+
* Highest Response Ratio Next (HRRN) scheduling algorithm.
9+
* HRRN is a non-preemptive scheduling algorithm that selects the process with
10+
* the highest response ratio for execution.
11+
* The response ratio is calculated as:
12+
*
13+
* <pre>
14+
* Response Ratio = (waiting time + burst time) / burst time
15+
* </pre>
16+
*
17+
* HRRN is designed to reduce the average waiting time and improve overall
18+
* system performance by balancing between short and long processes,
19+
* minimizing process starvation.
20+
*/
21+
public final class HighestResponseRatioNextScheduling {
22+
23+
private static final int PROCESS_NOT_FOUND = -1;
24+
private static final double INITIAL_MAX_RESPONSE_RATIO = -1.0;
25+
26+
private HighestResponseRatioNextScheduling() {
27+
}
28+
29+
/**
30+
* Represents a process in the scheduling algorithm.
31+
*/
32+
private static class Process {
33+
String name;
34+
int arrivalTime;
35+
int burstTime;
36+
int turnAroundTime;
37+
boolean finished;
38+
39+
Process(String name, int arrivalTime, int burstTime) {
40+
this.name = name;
41+
this.arrivalTime = arrivalTime;
42+
this.burstTime = burstTime;
43+
this.turnAroundTime = 0;
44+
this.finished = false;
45+
}
46+
47+
/**
48+
* Calculates the response ratio for this process.
49+
*
50+
* @param currentTime The current time in the scheduling process.
51+
* @return The response ratio for this process.
52+
*/
53+
double calculateResponseRatio(int currentTime) {
54+
return (double) (burstTime + currentTime - arrivalTime) / burstTime;
55+
}
56+
}
57+
58+
/**
59+
* Calculates the Turn Around Time (TAT) for each process.
60+
*
61+
* <p>Turn Around Time is calculated as the total time a process spends
62+
* in the system from arrival to completion. It is the sum of the burst time
63+
* and the waiting time.</p>
64+
*
65+
* @param processNames Array of process names.
66+
* @param arrivalTimes Array of arrival times corresponding to each process.
67+
* @param burstTimes Array of burst times for each process.
68+
* @param noOfProcesses The number of processes.
69+
* @return An array of Turn Around Times for each process.
70+
*/
71+
public static int[] calculateTurnAroundTime(final String[] processNames, final int[] arrivalTimes, final int[] burstTimes, final int noOfProcesses) {
72+
int currentTime = 0;
73+
int[] turnAroundTime = new int[noOfProcesses];
74+
Process[] processes = new Process[noOfProcesses];
75+
76+
for (int i = 0; i < noOfProcesses; i++) {
77+
processes[i] = new Process(processNames[i], arrivalTimes[i], burstTimes[i]);
78+
}
79+
80+
Arrays.sort(processes, Comparator.comparingInt(p -> p.arrivalTime));
81+
82+
int finishedProcessCount = 0;
83+
while (finishedProcessCount < noOfProcesses) {
84+
int nextProcessIndex = findNextProcess(processes, currentTime);
85+
if (nextProcessIndex == PROCESS_NOT_FOUND) {
86+
currentTime++;
87+
continue;
88+
}
89+
90+
Process currentProcess = processes[nextProcessIndex];
91+
currentTime = Math.max(currentTime, currentProcess.arrivalTime);
92+
currentProcess.turnAroundTime = currentTime + currentProcess.burstTime - currentProcess.arrivalTime;
93+
currentTime += currentProcess.burstTime;
94+
currentProcess.finished = true;
95+
finishedProcessCount++;
96+
}
97+
98+
for (int i = 0; i < noOfProcesses; i++) {
99+
turnAroundTime[i] = processes[i].turnAroundTime;
100+
}
101+
102+
return turnAroundTime;
103+
}
104+
105+
/**
106+
* Calculates the Waiting Time (WT) for each process.
107+
*
108+
* @param turnAroundTime The Turn Around Times for each process.
109+
* @param burstTimes The burst times for each process.
110+
* @return An array of Waiting Times for each process.
111+
*/
112+
public static int[] calculateWaitingTime(int[] turnAroundTime, int[] burstTimes) {
113+
int[] waitingTime = new int[turnAroundTime.length];
114+
for (int i = 0; i < turnAroundTime.length; i++) {
115+
waitingTime[i] = turnAroundTime[i] - burstTimes[i];
116+
}
117+
return waitingTime;
118+
}
119+
120+
/**
121+
* Finds the next process to be scheduled based on arrival times and the current time.
122+
*
123+
* @param processes Array of Process objects.
124+
* @param currentTime The current time in the scheduling process.
125+
* @return The index of the next process to be scheduled, or PROCESS_NOT_FOUND if no process is ready.
126+
*/
127+
private static int findNextProcess(Process[] processes, int currentTime) {
128+
return findHighestResponseRatio(processes, currentTime);
129+
}
130+
131+
/**
132+
* Finds the process with the highest response ratio.
133+
*
134+
* <p>The response ratio is calculated as:
135+
* (waiting time + burst time) / burst time
136+
* where waiting time = current time - arrival time</p>
137+
*
138+
* @param processes Array of Process objects.
139+
* @param currentTime The current time in the scheduling process.
140+
* @return The index of the process with the highest response ratio, or PROCESS_NOT_FOUND if no process is ready.
141+
*/
142+
private static int findHighestResponseRatio(Process[] processes, int currentTime) {
143+
double maxResponseRatio = INITIAL_MAX_RESPONSE_RATIO;
144+
int maxIndex = PROCESS_NOT_FOUND;
145+
146+
for (int i = 0; i < processes.length; i++) {
147+
Process process = processes[i];
148+
if (!process.finished && process.arrivalTime <= currentTime) {
149+
double responseRatio = process.calculateResponseRatio(currentTime);
150+
if (responseRatio > maxResponseRatio) {
151+
maxResponseRatio = responseRatio;
152+
maxIndex = i;
153+
}
154+
}
155+
}
156+
return maxIndex;
157+
}
158+
}
Lines changed: 112 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,112 @@
1+
package com.thealgorithms.scheduling;
2+
3+
import static org.junit.jupiter.api.Assertions.assertArrayEquals;
4+
5+
import org.junit.jupiter.api.Test;
6+
7+
public class HighestResponseRatioNextSchedulingTest {
8+
9+
@Test
10+
public void testCalculateTurnAroundTime() {
11+
String[] processNames = {"A", "B", "C"};
12+
int[] arrivalTimes = {0, 2, 4};
13+
int[] burstTimes = {3, 1, 2};
14+
int noOfProcesses = 3;
15+
16+
int[] expectedTurnAroundTimes = {3, 2, 2};
17+
int[] actualTurnAroundTimes = HighestResponseRatioNextScheduling.calculateTurnAroundTime(processNames, arrivalTimes, burstTimes, noOfProcesses);
18+
19+
assertArrayEquals(expectedTurnAroundTimes, actualTurnAroundTimes, "Turn Around Times do not match");
20+
}
21+
22+
@Test
23+
public void testCalculateWaitingTime() {
24+
int[] turnAroundTimes = {3, 1, 5};
25+
int[] burstTimes = {3, 1, 2};
26+
27+
int[] expectedWaitingTimes = {0, 0, 3};
28+
int[] actualWaitingTimes = HighestResponseRatioNextScheduling.calculateWaitingTime(turnAroundTimes, burstTimes);
29+
30+
assertArrayEquals(expectedWaitingTimes, actualWaitingTimes, "Waiting Times do not match");
31+
}
32+
33+
@Test
34+
public void testCompleteSchedulingScenario() {
35+
String[] processNames = {"A", "B", "C"};
36+
int[] arrivalTimes = {0, 1, 2};
37+
int[] burstTimes = {5, 2, 1};
38+
39+
int[] expectedTurnAroundTimes = {5, 7, 4};
40+
int[] turnAroundTimes = HighestResponseRatioNextScheduling.calculateTurnAroundTime(processNames, arrivalTimes, burstTimes, processNames.length);
41+
assertArrayEquals(expectedTurnAroundTimes, turnAroundTimes, "Turn Around Times do not match");
42+
43+
int[] expectedWaitingTimes = {0, 5, 3};
44+
int[] waitingTimes = HighestResponseRatioNextScheduling.calculateWaitingTime(turnAroundTimes, burstTimes);
45+
assertArrayEquals(expectedWaitingTimes, waitingTimes, "Waiting Times do not match");
46+
}
47+
48+
@Test
49+
public void testZeroProcesses() {
50+
String[] processNames = {};
51+
int[] arrivalTimes = {};
52+
int[] burstTimes = {};
53+
int noOfProcesses = 0;
54+
55+
int[] expectedTurnAroundTimes = {};
56+
int[] actualTurnAroundTimes = HighestResponseRatioNextScheduling.calculateTurnAroundTime(processNames, arrivalTimes, burstTimes, noOfProcesses);
57+
58+
assertArrayEquals(expectedTurnAroundTimes, actualTurnAroundTimes, "Turn Around Times for zero processes should be an empty array");
59+
}
60+
61+
@Test
62+
public void testAllProcessesArriveAtSameTime() {
63+
String[] processNames = {"A", "B", "C", "D"};
64+
int[] arrivalTimes = {0, 0, 0, 0};
65+
int[] burstTimes = {4, 3, 1, 2};
66+
int noOfProcesses = 4;
67+
68+
int[] expectedTurnAroundTimes = {4, 10, 5, 7};
69+
int[] actualTurnAroundTimes = HighestResponseRatioNextScheduling.calculateTurnAroundTime(processNames, arrivalTimes, burstTimes, noOfProcesses);
70+
71+
assertArrayEquals(expectedTurnAroundTimes, actualTurnAroundTimes, "Turn Around Times for processes arriving at the same time do not match");
72+
}
73+
74+
@Test
75+
public void testProcessesWithZeroBurstTime() {
76+
String[] processNames = {"A", "B", "C"};
77+
int[] arrivalTimes = {0, 1, 2};
78+
int[] burstTimes = {3, 0, 2};
79+
int noOfProcesses = 3;
80+
81+
int[] expectedTurnAroundTimes = {3, 2, 3};
82+
int[] actualTurnAroundTimes = HighestResponseRatioNextScheduling.calculateTurnAroundTime(processNames, arrivalTimes, burstTimes, noOfProcesses);
83+
84+
assertArrayEquals(expectedTurnAroundTimes, actualTurnAroundTimes, "Turn Around Times for processes with zero burst time do not match");
85+
}
86+
87+
@Test
88+
public void testProcessesWithLargeGapsBetweenArrivals() {
89+
String[] processNames = {"A", "B", "C"};
90+
int[] arrivalTimes = {0, 100, 200};
91+
int[] burstTimes = {10, 10, 10};
92+
int noOfProcesses = 3;
93+
94+
int[] expectedTurnAroundTimes = {10, 10, 10};
95+
int[] actualTurnAroundTimes = HighestResponseRatioNextScheduling.calculateTurnAroundTime(processNames, arrivalTimes, burstTimes, noOfProcesses);
96+
97+
assertArrayEquals(expectedTurnAroundTimes, actualTurnAroundTimes, "Turn Around Times for processes with large gaps between arrivals do not match");
98+
}
99+
100+
@Test
101+
public void testProcessesWithVeryLargeBurstTimes() {
102+
String[] processNames = {"A", "B"};
103+
int[] arrivalTimes = {0, 1};
104+
int[] burstTimes = {Integer.MAX_VALUE / 2, Integer.MAX_VALUE / 2};
105+
int noOfProcesses = 2;
106+
107+
int[] expectedTurnAroundTimes = {Integer.MAX_VALUE / 2, Integer.MAX_VALUE - 2};
108+
int[] actualTurnAroundTimes = HighestResponseRatioNextScheduling.calculateTurnAroundTime(processNames, arrivalTimes, burstTimes, noOfProcesses);
109+
110+
assertArrayEquals(expectedTurnAroundTimes, actualTurnAroundTimes, "Turn Around Times for processes with very large burst times do not match");
111+
}
112+
}

0 commit comments

Comments
 (0)