Skip to content

Commit 6822f20

Browse files
committed
2 parents 3aa80c6 + 0acdc25 commit 6822f20

File tree

4 files changed

+236
-70
lines changed

4 files changed

+236
-70
lines changed

DIRECTORY.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -161,6 +161,7 @@
161161

162162
## Greedy Algorithms
163163
* [Boruvkas Minimum Spanning Tree](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/greedy_algorithms/boruvkas_minimum_spanning_tree.cpp)
164+
* [Digit Separation](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/greedy_algorithms/digit_separation.cpp)
164165
* [Dijkstra](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/greedy_algorithms/dijkstra.cpp)
165166
* [Gale Shapley](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/greedy_algorithms/gale_shapley.cpp)
166167
* [Huffman](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/greedy_algorithms/huffman.cpp)
@@ -300,6 +301,8 @@
300301
* [Iterative Tree Traversals](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/others/iterative_tree_traversals.cpp)
301302
* [Kadanes3](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/others/kadanes3.cpp)
302303
* [Kelvin To Celsius](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/others/kelvin_to_celsius.cpp)
304+
* [Lfu Cache](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/others/lfu_cache.cpp)
305+
* [Longest Substring Without Repeating Characters](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/others/longest_substring_without_repeating_characters.cpp)
303306
* [Lru Cache](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/others/lru_cache.cpp)
304307
* [Matrix Exponentiation](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/others/matrix_exponentiation.cpp)
305308
* [Palindrome Of Number](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/others/palindrome_of_number.cpp)
@@ -369,6 +372,7 @@
369372
* [Gnome Sort](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/sorting/gnome_sort.cpp)
370373
* [Heap Sort](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/sorting/heap_sort.cpp)
371374
* [Insertion Sort](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/sorting/insertion_sort.cpp)
375+
* [Insertion Sort Recursive](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/sorting/insertion_sort_recursive.cpp)
372376
* [Library Sort](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/sorting/library_sort.cpp)
373377
* [Merge Insertion Sort](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/sorting/merge_insertion_sort.cpp)
374378
* [Merge Sort](https://github.com/TheAlgorithms/C-Plus-Plus/blob/HEAD/sorting/merge_sort.cpp)

greedy_algorithms/job_sequencing_algorithm.cpp

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -80,13 +80,14 @@
8080
namespace greedy_algorithms {
8181

8282
/**
83+
* @struct Job
8384
* @brief A structure to represent a job
8485
*/
8586
struct Job {
86-
char id; // Job Id
87-
int dead; // Deadline of job
88-
int profit; // Profit earned if job is completed before deadline
89-
}; // namespace greedy_algorithmsstruct Job
87+
char id; ///< Job Id
88+
int dead; ///< Deadline of job
89+
int profit; ///< Profit earned if job is completed before deadline
90+
};
9091

9192
/**
9293
* @brief Utility function that finds Custom sorting helper
Lines changed: 110 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,110 @@
1+
/**
2+
* @file
3+
* @brief Solution for Longest Substring Without Repeating Characters problem.
4+
* @details
5+
* Problem link: https://leetcode.com/problems/longest-substring-without-repeating-characters/description/
6+
*
7+
* Intuition:
8+
* 1) The intuition is straightforward and simple. We track the frequency of characters.
9+
* 2) Since we can't use a string to track the longest substring without repeating characters efficiently (as removing a character from the front of a string isn't O(1)), we optimize the solution using a deque approach.
10+
*
11+
* Approach:
12+
* 1) Initialize an unordered_map to track the frequency of characters.
13+
* 2) Use a deque for pushing characters, and update the result deque (`res`) with the current deque (`temp`)
14+
* whenever we find a longer substring.
15+
* 3) Use a while loop to reduce the frequency from the front, incrementing `i`,
16+
* and removing characters from the `temp` deque as we no longer need them.
17+
* 4) Return `res.size()` as we are interested in the length of the longest substring.
18+
*
19+
* Time Complexity: O(N)
20+
* Space Complexity: O(N)
21+
*
22+
* I hope this helps to understand.
23+
* Thank you!
24+
* @author [Ashish Kumar Sahoo](github.com/ashish5kmax)
25+
**/
26+
27+
#include <iostream> // for IO Operations
28+
#include <unordered_map> // for std::unordered_map
29+
#include <deque> // for std::deque
30+
#include <string> // for string class/string datatype which is taken as input
31+
#include <cassert> // for assert
32+
33+
/**
34+
* @class Longest_Substring
35+
* @brief Class that solves the Longest Substring Without Repeating Characters problem.
36+
*/
37+
class Longest_Substring {
38+
public:
39+
/**
40+
* @brief Function to find the length of the longest substring without repeating characters.
41+
* @param s Input string.
42+
* @return Length of the longest substring.
43+
*/
44+
int lengthOfLongestSubstring(std::string s) {
45+
// If the size of string is 1, then it will be the answer.
46+
if (s.size() == 1) return 1;
47+
48+
// Map used to store the character frequency.
49+
std::unordered_map<char, int> m;
50+
int n = s.length();
51+
52+
// Deque to remove from back if repeating characters are present.
53+
std::deque<char> temp;
54+
std::deque<char> res;
55+
int i, j;
56+
57+
// Sliding window approach using two pointers.
58+
for (i = 0, j = 0; i < n && j < n;) {
59+
m[s[j]]++;
60+
61+
// If repeating character found, update result and remove from the front.
62+
if (m[s[j]] > 1) {
63+
if (temp.size() > res.size()) {
64+
res = temp;
65+
}
66+
67+
while (m[s[j]] > 1) {
68+
temp.pop_front();
69+
m[s[i]]--;
70+
i++;
71+
}
72+
}
73+
74+
// Add the current character to the deque.
75+
temp.push_back(s[j]);
76+
j++;
77+
}
78+
79+
// Final check to update result.
80+
if (temp.size() > res.size()) {
81+
res = temp;
82+
}
83+
84+
return res.size(); // Return the length of the longest substring.
85+
}
86+
};
87+
88+
/**
89+
* @brief Self-test implementations
90+
* @returns void
91+
*/
92+
static void tests() {
93+
Longest_Substring soln;
94+
assert(soln.lengthOfLongestSubstring("abcabcbb") == 3);
95+
assert(soln.lengthOfLongestSubstring("bbbbb") == 1);
96+
assert(soln.lengthOfLongestSubstring("pwwkew") == 3);
97+
assert(soln.lengthOfLongestSubstring("") == 0); // Test case for empty string
98+
assert(soln.lengthOfLongestSubstring("abcdef") == 6); // Test case for all unique characters
99+
assert(soln.lengthOfLongestSubstring("a") == 1); // Single character
100+
std::cout << "All test cases passed!" << std::endl;
101+
}
102+
103+
/**
104+
* @brief Main function.
105+
* @return 0 on successful execution.
106+
*/
107+
int main() {
108+
tests(); // run self-test implementations
109+
return 0;
110+
}

sorting/bubble_sort.cpp

Lines changed: 117 additions & 66 deletions
Original file line numberDiff line numberDiff line change
@@ -2,82 +2,133 @@
22
* @file
33
* @brief Bubble sort algorithm
44
*
5-
* The working principle of the Bubble sort algorithm:
5+
* @details
6+
* Bubble sort algorithm is the bubble sorting algorithm. The most important reason
7+
* for calling the bubble is that the largest number is thrown at the end of this
8+
* algorithm. This is all about the logic. In each iteration, the largest number is
9+
* expired and when iterations are completed, the sorting takes place.
10+
*
11+
* What is Swap?
12+
*
13+
* Swap in the software means that two variables are displaced.
14+
* An additional variable is required for this operation. x = 5, y = 10.
15+
* We want x = 10, y = 5. Here we create the most variable to do it.
16+
*
17+
* ```cpp
18+
* int z;
19+
* z = x;
20+
* x = y;
21+
* y = z;
22+
* ```
23+
*
24+
* The above process is a typical displacement process.
25+
* When x assigns the value to x, the old value of x is lost.
26+
* That's why we created a variable z to create the first value of the value of x,
27+
* and finally, we have assigned to y.
28+
*
29+
* ## Bubble Sort Algorithm Analysis (Best Case - Worst Case - Average Case)
30+
*
31+
* ### Best Case
32+
* Bubble Sort Best Case Performance. \f$O(n)\f$. However, you
33+
* can't get the best status in the code we shared above. This happens on the
34+
* optimized bubble sort algorithm. It's right down there.
35+
*
36+
* ### Worst Case
37+
* Bubble Sort Worst Case Performance is \f$O(n^{2})\f$. Why is that? Because if you
38+
* remember Big O Notation, we were calculating the complexity of the algorithms in
39+
* the nested loops. The \f$n * (n - 1)\f$ product gives us \f$O(n^{2})\f$ performance. In the
40+
* worst case all the steps of the cycle will occur.
41+
*
42+
* ### Average Case
43+
* Bubble Sort is not an optimal algorithm. In average, \f$O(n^{2})\f$ performance is taken.
44+
*
45+
* @author [Deepak](https://github.com/Deepak-j-p)
46+
* @author [Nguyen Phuc Chuong](https://github.com/hollowcrust)
47+
*/
648

7-
Bubble sort algorithm is the bubble sorting algorithm. The most important reason
8-
for calling the bubble is that the largest number is thrown at the end of this
9-
algorithm. This is all about the logic. In each iteration, the largest number is
10-
expired and when iterations are completed, the sorting takes place.
49+
#include <algorithm> /// for std::is_sorted
50+
#include <cassert> /// for assert
51+
#include <iostream> /// for IO implementations
52+
#include <string> /// for std::string
53+
#include <utility> /// for std::pair, std::swap
54+
#include <vector> /// for std::vector, std::vector::push_back, std::vector::size
1155

12-
What is Swap?
56+
/**
57+
* @namespace sorting
58+
* @brief Sorting algorithms
59+
*/
60+
namespace sorting {
61+
/**
62+
* @namespace bubble_sort
63+
* @brief Bubble sort algorithm
64+
*/
65+
namespace bubble_sort {
66+
/**
67+
* @brief Bubble sort algorithm
68+
* @param array An array to be sorted
69+
* @return The array sorted in ascending order
70+
*/
71+
template <typename T>
72+
std::vector<T> bubble_sort(std::vector<T>& array) {
73+
// swap_check flag to terminate the function early
74+
// if there is no swap occurs in one iteration.
75+
bool swap_check = true;
76+
int size = array.size();
77+
for (int i = 0; (i < size) && (swap_check); i++) {
78+
swap_check = false;
79+
for (int j = 0; j < size - 1 - i; j++) {
80+
if (array[j] > array[j + 1]) {
81+
swap_check = true;
82+
std::swap(array[j], array[j + 1]);
83+
}
84+
}
85+
}
1386

14-
Swap in the software means that two variables are displaced.
15-
An additional variable is required for this operation. x = 5, y = 10.
16-
We want x = 10, y = 5. Here we create the most variable to do it.
87+
return array;
88+
}
89+
} // namespace bubble_sort
90+
} // namespace sorting
1791

18-
int z;
19-
z = x;
20-
x = y;
21-
y = z;
92+
/**
93+
* @brief Self-test implementation
94+
* @return void
95+
*/
96+
static void test() {
97+
std::vector<int> vec_1 = {3, 1, -9, 0};
98+
std::vector<int> sorted_1 = sorting::bubble_sort::bubble_sort(vec_1);
2299

23-
The above process is a typical displacement process.
24-
When x assigns the value to x, the old value of x is lost.
25-
That's why we created a variable z to create the first value of the value of x,
26-
and finally, we have assigned to y.
100+
std::vector<int> vec_2 = {3};
101+
std::vector<int> sorted_2 = sorting::bubble_sort::bubble_sort(vec_2);
27102

28-
Bubble Sort Algorithm Analysis (Best Case - Worst Case - Average Case)
103+
std::vector<int> vec_3 = {10, 10, 10, 10, 10};
104+
std::vector<int> sorted_3 = sorting::bubble_sort::bubble_sort(vec_3);
29105

30-
Bubble Sort Worst Case Performance is O (n²). Why is that? Because if you
31-
remember Big O Notation, we were calculating the complexity of the algorithms in
32-
the nested loops. The n * (n - 1) product gives us O (n²) performance. In the
33-
worst case all the steps of the cycle will occur. Bubble Sort (Avarage Case)
34-
Performance. Bubble Sort is not an optimal algorithm. in average, O (n²)
35-
performance is taken. Bubble Sort Best Case Performance. O (n). However, you
36-
can't get the best status in the code we shared above. This happens on the
37-
optimized bubble sort algorithm. It's right down there.
38-
*/
106+
std::vector<float> vec_4 = {1234, -273.1, 23, 150, 1234, 1555.55, -2000};
107+
std::vector<float> sorted_4 = sorting::bubble_sort::bubble_sort(vec_4);
39108

40-
#include <iostream>
41-
#include <vector>
109+
std::vector<char> vec_5 = {'z', 'Z', 'a', 'B', ' ', 'c', 'a'};
110+
std::vector<char> sorted_5 = sorting::bubble_sort::bubble_sort(vec_5);
42111

43-
int main() {
44-
int n;
45-
bool swap_check = true;
46-
std::cout << "Enter the amount of numbers to sort: ";
47-
std::cin >> n;
48-
std::vector<int> numbers;
49-
std::cout << "Enter " << n << " numbers: ";
50-
int num;
112+
std::vector<std::string> vec_6 = {"Hello", "hello", "Helo", "Hi", "hehe"};
113+
std::vector<std::string> sorted_6 = sorting::bubble_sort::bubble_sort(vec_6);
51114

52-
// Input
53-
for (int i = 0; i < n; i++) {
54-
std::cin >> num;
55-
numbers.push_back(num);
56-
}
115+
std::vector<std::pair<int, char>> vec_7 = {{10, 'c'}, {2, 'z'}, {10, 'a'}, {0, 'b'}, {-1, 'z'}};
116+
std::vector<std::pair<int, char>> sorted_7 = sorting::bubble_sort::bubble_sort(vec_7);
57117

58-
// Bubble Sorting
59-
for (int i = 0; (i < n) && (swap_check); i++) {
60-
swap_check = false;
61-
for (int j = 0; j < n - 1 - i; j++) {
62-
if (numbers[j] > numbers[j + 1]) {
63-
swap_check = true;
64-
std::swap(numbers[j],
65-
numbers[j + 1]); // by changing swap location.
66-
// I mean, j. If the number is
67-
// greater than j + 1, then it
68-
// means the location.
69-
}
70-
}
71-
}
118+
assert(std::is_sorted(sorted_1.begin(), sorted_1.end()));
119+
assert(std::is_sorted(sorted_2.begin(), sorted_2.end()));
120+
assert(std::is_sorted(sorted_3.begin(), sorted_3.end()));
121+
assert(std::is_sorted(sorted_4.begin(), sorted_4.end()));
122+
assert(std::is_sorted(sorted_5.begin(), sorted_5.end()));
123+
assert(std::is_sorted(sorted_6.begin(), sorted_6.end()));
124+
assert(std::is_sorted(sorted_7.begin(), sorted_7.end()));
125+
}
72126

73-
// Output
74-
std::cout << "\nSorted Array : ";
75-
for (int i = 0; i < numbers.size(); i++) {
76-
if (i != numbers.size() - 1) {
77-
std::cout << numbers[i] << ", ";
78-
} else {
79-
std::cout << numbers[i] << std::endl;
80-
}
81-
}
82-
return 0;
127+
/**
128+
* @brief Main function
129+
* @return 0 on exit
130+
*/
131+
int main() {
132+
test();
133+
return 0;
83134
}

0 commit comments

Comments
 (0)