Skip to content

Commit cf176af

Browse files
committed
Merge remote-tracking branch 'origin/refactor/ceil' into refactor/ceil
2 parents a773cfc + b4e691e commit cf176af

File tree

5 files changed

+132
-185
lines changed

5 files changed

+132
-185
lines changed

src/main/java/com/thealgorithms/others/TwoPointers.java

Lines changed: 20 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -7,30 +7,37 @@
77
* <p>
88
* Link: https://www.geeksforgeeks.org/two-pointers-technique/
99
*/
10-
final class TwoPointers {
10+
public final class TwoPointers {
11+
1112
private TwoPointers() {
1213
}
1314

1415
/**
15-
* Given a sorted array arr (sorted in ascending order), find if there exists
16-
* any pair of elements such that their sum is equal to the key.
16+
* Checks whether there exists a pair of elements in a sorted array whose sum equals the specified key.
1717
*
18-
* @param arr the array containing elements (must be sorted in ascending order)
19-
* @param key the number to search
20-
* @return {@code true} if there exists a pair of elements, {@code false} otherwise.
18+
* @param arr a sorted array of integers in ascending order (must not be null)
19+
* @param key the target sum to find
20+
* @return {@code true} if there exists at least one pair whose sum equals {@code key}, {@code false} otherwise
21+
* @throws IllegalArgumentException if {@code arr} is {@code null}
2122
*/
2223
public static boolean isPairedSum(int[] arr, int key) {
23-
int i = 0; // index of the first element
24-
int j = arr.length - 1; // index of the last element
24+
if (arr == null) {
25+
throw new IllegalArgumentException("Input array must not be null.");
26+
}
27+
28+
int left = 0;
29+
int right = arr.length - 1;
30+
31+
while (left < right) {
32+
int sum = arr[left] + arr[right];
2533

26-
while (i < j) {
27-
int sum = arr[i] + arr[j];
2834
if (sum == key) {
2935
return true;
30-
} else if (sum < key) {
31-
i++;
36+
}
37+
if (sum < key) {
38+
left++;
3239
} else {
33-
j--;
40+
right--;
3441
}
3542
}
3643
return false;
Lines changed: 33 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,36 +1,52 @@
11
package com.thealgorithms.recursion;
22

3-
// program to find power set of a string
4-
53
import java.util.ArrayList;
64
import java.util.List;
75

6+
/**
7+
* Utility class to generate all subsets (power set) of a given string using recursion.
8+
*
9+
* <p>For example, the string "ab" will produce: ["ab", "a", "b", ""]
10+
*/
811
public final class GenerateSubsets {
912

1013
private GenerateSubsets() {
11-
throw new UnsupportedOperationException("Utility class");
1214
}
1315

16+
/**
17+
* Generates all subsets (power set) of the given string using recursion.
18+
*
19+
* @param str the input string to generate subsets for
20+
* @return a list of all subsets of the input string
21+
*/
1422
public static List<String> subsetRecursion(String str) {
15-
return doRecursion("", str);
23+
return generateSubsets("", str);
1624
}
1725

18-
private static List<String> doRecursion(String p, String up) {
19-
if (up.isEmpty()) {
20-
List<String> list = new ArrayList<>();
21-
list.add(p);
22-
return list;
26+
/**
27+
* Recursive helper method to generate subsets by including or excluding characters.
28+
*
29+
* @param current the current prefix being built
30+
* @param remaining the remaining string to process
31+
* @return list of subsets formed from current and remaining
32+
*/
33+
private static List<String> generateSubsets(String current, String remaining) {
34+
if (remaining.isEmpty()) {
35+
List<String> result = new ArrayList<>();
36+
result.add(current);
37+
return result;
2338
}
2439

25-
// Taking the character
26-
char ch = up.charAt(0);
27-
// Adding the character in the recursion
28-
List<String> left = doRecursion(p + ch, up.substring(1));
29-
// Not adding the character in the recursion
30-
List<String> right = doRecursion(p, up.substring(1));
40+
char ch = remaining.charAt(0);
41+
String next = remaining.substring(1);
42+
43+
// Include the character
44+
List<String> withChar = generateSubsets(current + ch, next);
3145

32-
left.addAll(right);
46+
// Exclude the character
47+
List<String> withoutChar = generateSubsets(current, next);
3348

34-
return left;
49+
withChar.addAll(withoutChar);
50+
return withChar;
3551
}
3652
}

src/main/java/com/thealgorithms/scheduling/SJFScheduling.java

Lines changed: 43 additions & 66 deletions
Original file line numberDiff line numberDiff line change
@@ -2,78 +2,62 @@
22

33
import com.thealgorithms.devutils.entities.ProcessDetails;
44
import java.util.ArrayList;
5+
import java.util.Collection;
6+
import java.util.Comparator;
7+
import java.util.Iterator;
58
import java.util.List;
69

710
/**
8-
* Implementation of Shortest Job First Algorithm: The algorithm allows the waiting process with the
9-
* minimal burst time to be executed first. see more here:
10-
* https://www.guru99.com/shortest-job-first-sjf-scheduling.html
11+
* Shortest Job First (SJF) Scheduling Algorithm:
12+
* Executes processes with the shortest burst time first among the ones that have arrived.
1113
*/
12-
1314
public class SJFScheduling {
14-
protected ArrayList<ProcessDetails> processes;
15-
protected ArrayList<String> schedule;
16-
17-
private static void sortProcessesByArrivalTime(List<ProcessDetails> processes) {
18-
for (int i = 0; i < processes.size(); i++) {
19-
for (int j = i + 1; j < processes.size() - 1; j++) {
20-
if (processes.get(j).getArrivalTime() > processes.get(j + 1).getArrivalTime()) {
21-
final var temp = processes.get(j);
22-
processes.set(j, processes.get(j + 1));
23-
processes.set(j + 1, temp);
24-
}
25-
}
26-
}
27-
}
15+
private final List<ProcessDetails> processes;
16+
private final List<String> schedule;
2817

29-
/**
30-
* a simple constructor
31-
* @param processes a list of processes the user wants to schedule
32-
* it also sorts the processes based on the time of their arrival
33-
*/
34-
SJFScheduling(final ArrayList<ProcessDetails> processes) {
35-
this.processes = processes;
36-
schedule = new ArrayList<>();
18+
public SJFScheduling(final List<ProcessDetails> processes) {
19+
this.processes = new ArrayList<>(processes);
20+
this.schedule = new ArrayList<>();
3721
sortProcessesByArrivalTime(this.processes);
3822
}
39-
protected void sortByArrivalTime() {
40-
sortProcessesByArrivalTime(processes);
23+
24+
private static void sortProcessesByArrivalTime(List<ProcessDetails> processes) {
25+
processes.sort(Comparator.comparingInt(ProcessDetails::getArrivalTime));
4126
}
4227

4328
/**
44-
* this functions returns the order of the executions
29+
* Executes the SJF scheduling algorithm and builds the execution order.
4530
*/
46-
4731
public void scheduleProcesses() {
48-
ArrayList<ProcessDetails> ready = new ArrayList<>();
49-
32+
List<ProcessDetails> ready = new ArrayList<>();
5033
int size = processes.size();
51-
int runtime;
5234
int time = 0;
5335
int executed = 0;
54-
int j;
55-
int k = 0;
56-
ProcessDetails running;
5736

58-
if (size == 0) {
59-
return;
37+
Iterator<ProcessDetails> processIterator = processes.iterator();
38+
39+
// This will track the next process to be checked for arrival time
40+
ProcessDetails nextProcess = null;
41+
if (processIterator.hasNext()) {
42+
nextProcess = processIterator.next();
6043
}
6144

6245
while (executed < size) {
63-
while (k < size && processes.get(k).getArrivalTime() <= time) // here we find the processes that have arrived.
64-
{
65-
ready.add(processes.get(k));
66-
k++;
46+
// Load all processes that have arrived by current time
47+
while (nextProcess != null && nextProcess.getArrivalTime() <= time) {
48+
ready.add(nextProcess);
49+
if (processIterator.hasNext()) {
50+
nextProcess = processIterator.next();
51+
} else {
52+
nextProcess = null;
53+
}
6754
}
6855

69-
running = findShortestJob(ready);
56+
ProcessDetails running = findShortestJob(ready);
7057
if (running == null) {
7158
time++;
7259
} else {
73-
runtime = running.getBurstTime();
74-
for (j = 0; j < runtime; j++) {
75-
time++;
76-
}
60+
time += running.getBurstTime();
7761
schedule.add(running.getProcessId());
7862
ready.remove(running);
7963
executed++;
@@ -82,30 +66,23 @@ public void scheduleProcesses() {
8266
}
8367

8468
/**
85-
* this function evaluates the shortest job of all the ready processes (based on a process
86-
* burst time)
69+
* Finds the process with the shortest job of all the ready processes (based on a process
8770
* @param readyProcesses an array list of ready processes
8871
* @return returns the process' with the shortest burst time OR NULL if there are no ready
8972
* processes
9073
*/
91-
private ProcessDetails findShortestJob(List<ProcessDetails> readyProcesses) {
92-
if (readyProcesses.isEmpty()) {
93-
return null;
94-
}
95-
int i;
96-
int size = readyProcesses.size();
97-
int minBurstTime = readyProcesses.get(0).getBurstTime();
98-
int temp;
99-
int positionOfShortestJob = 0;
74+
private ProcessDetails findShortestJob(Collection<ProcessDetails> readyProcesses) {
75+
return readyProcesses.stream().min(Comparator.comparingInt(ProcessDetails::getBurstTime)).orElse(null);
76+
}
10077

101-
for (i = 1; i < size; i++) {
102-
temp = readyProcesses.get(i).getBurstTime();
103-
if (minBurstTime > temp) {
104-
minBurstTime = temp;
105-
positionOfShortestJob = i;
106-
}
107-
}
78+
/**
79+
* Returns the computed schedule after calling scheduleProcesses().
80+
*/
81+
public List<String> getSchedule() {
82+
return schedule;
83+
}
10884

109-
return readyProcesses.get(positionOfShortestJob);
85+
public List<ProcessDetails> getProcesses() {
86+
return List.copyOf(processes);
11087
}
11188
}

src/test/java/com/thealgorithms/others/TwoPointersTest.java

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
package com.thealgorithms.others;
22

3+
import static org.junit.jupiter.api.Assertions.assertEquals;
34
import static org.junit.jupiter.api.Assertions.assertFalse;
5+
import static org.junit.jupiter.api.Assertions.assertThrows;
46
import static org.junit.jupiter.api.Assertions.assertTrue;
57

68
import org.junit.jupiter.api.Test;
@@ -69,4 +71,10 @@ void testPairExistsAtEdges() {
6971
int key = 9;
7072
assertTrue(TwoPointers.isPairedSum(arr, key));
7173
}
74+
75+
@Test
76+
void isPairedSumShouldThrowExceptionWhenArrayIsNull() {
77+
IllegalArgumentException exception = assertThrows(IllegalArgumentException.class, () -> TwoPointers.isPairedSum(null, 10));
78+
assertEquals("Input array must not be null.", exception.getMessage());
79+
}
7280
}

0 commit comments

Comments
 (0)