-
-
Notifications
You must be signed in to change notification settings - Fork 7.3k
/
Copy pathinsertion_sort_recursive.cpp
152 lines (137 loc) · 4.18 KB
/
insertion_sort_recursive.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
/**
* @file
* @brief Insertion Sort Algorithm
* @author [Dhanush S](https://github.com/Fandroid745)
*
* @details
* Insertion sort is a simple sorting algorithm that builds the final
* sorted array one element at a time. It is much less efficient compared
* to other sorting algorithms like heap sort, merge sort, or quick sort.
*
* However, it has several advantages:
* - Easy to implement.
* - Efficient for small data sets.
* - More efficient than other O(n²) algorithms like selection sort or bubble sort.
* - Stable: it does not change the relative order of elements with equal keys.
*
* Insertion sort works similarly to how people sort playing cards in their hands.
* The algorithm iterates through the list and inserts each element into its correct
* position in the sorted portion of the array.
*
* The time complexity of the algorithm is \f$O(n^2)\f$, and in some cases, it
* can be \f$O(n)\f$.
*
* Example execution:
* 1. Start with the array [4, 3, 2, 5, 1].
* 2. Insert 3 in its correct position: [3, 4, 2, 5, 1].
* 3. Insert 2: [2, 3, 4, 5, 1].
* 4. Continue this until the array is sorted: [1, 2, 3, 4, 5].
*/
#include <algorithm> /// for std::is_sorted
#include <cassert> /// for assert function in testing
#include <iostream> /// for std::cout and std::endl
#include <vector> /// for using std::vector
/**
* @namespace sorting
* @brief Contains sorting algorithms
*/
namespace sorting {
/**
* @brief Insertion Sort Function
*
* @tparam T Type of the array elements
* @param[in,out] arr Array to be sorted
* @param n Size of the array
*/
template <typename T>
void insertionSort(T *arr, int n) {
for (int i = 1; i < n; i++) {
T temp = arr[i];
int j = i - 1;
while (j >= 0 && temp < arr[j]) {
arr[j + 1] = arr[j];
j--;
}
arr[j + 1] = temp;
}
}
/**
* @brief Insertion Sort for a vector
*
* @tparam T Type of the vector elements
* @param [in,out] arr Pointer to the vector to be sorted
*/
template <typename T>
void insertionSort(std::vector<T> *arr) {
size_t n = arr->size();
for (size_t i = 1; i < n; i++) {
T temp = arr->at(i);
int32_t j = i - 1;
while (j >= 0 && temp < arr->at(j)) {
arr->at(j + 1) = arr->at(j);
j--;
}
arr->at(j + 1) = temp;
}
}
} // namespace sorting
/**
* @brief Helper function to create a random array
*
* @tparam T Type of the array elements
* @param arr Array to fill (must be pre-allocated)
* @param N Number of elements in the array
*/
template <typename T>
static void create_random_array(T *arr, int N) {
while (N--) {
double r = (std::rand() % 10000 - 5000) / 100.f;
arr[N] = static_cast<T>(r);
}
}
/**
* @brief self test implementation
* @return void
*/
static void tests() {
int arr1[10] = {78, 34, 35, 6, 34, 56, 3, 56, 2, 4};
std::cout << "Test 1... ";
sorting::insertionSort(arr1, 10);
assert(std::is_sorted(arr1, arr1 + 10));
std::cout << "passed" << std::endl;
int arr2[5] = {5, -3, 7, -2, 1};
std::cout << "Test 2... ";
sorting::insertionSort(arr2, 5);
assert(std::is_sorted(arr2, arr2 + 5));
std::cout << "passed" << std::endl;
float arr3[5] = {5.6, -3.1, -3.0, -2.1, 1.8};
std::cout << "Test 3... ";
sorting::insertionSort(arr3, 5);
assert(std::is_sorted(arr3, arr3 + 5));
std::cout << "passed" << std::endl;
std::vector<float> arr4({5.6, -3.1, -3.0, -2.1, 1.8});
std::cout << "Test 4... ";
sorting::insertionSort(&arr4);
assert(std::is_sorted(std::begin(arr4), std::end(arr4)));
std::cout << "passed" << std::endl;
int arr5[50];
std::cout << "Test 5... ";
create_random_array(arr5, 50);
sorting::insertionSort(arr5, 50);
assert(std::is_sorted(arr5, arr5 + 50));
std::cout << "passed" << std::endl;
float arr6[50];
std::cout << "Test 6... ";
create_random_array(arr6, 50);
sorting::insertionSort(arr6, 50);
assert(std::is_sorted(arr6, arr6 + 50));
std::cout << "passed" << std::endl;
}
/**
* @brief Main function
* @return 0 on successful exit.
*/
int main() {
tests(); /// run self test implementations
return 0;
}