Sorts
Sorts

Insetion Sort
The insertion sort algorithm iterates through an input array and removes one element per iteration, finds the place the element belongs in the array, and then places it there. This process grows a sorted list from left to right. The algorithm is as follows:
To sort an array of size n in ascending order:
Iterate from arr[1] to arr[n] over the array.
Compare the current element (key) to its predecessor.
If the key element is smaller than its predecessor, compare it to the elements before. Move the greater elements one position up to make space for the swapped element.
The key is that: arr[i - 1] is always sorted.

Implementation
1 | def insertion_sort(lst): |
Merge Sort
Mergesort has two steps: merging and sorting. The algorithm uses a divide-and-conquer approach to merge and sort a list.
Divide and conquer is a technique used for breaking algorithms down into subproblems, solving the subproblems, and then combining the results back together to solve the original problem. It can be helpful to think of this method as divide, conquer, and combine.
The mergesort algorithm focuses on how to merge together two pre-sorted arrays such that the resulting array is also sorted. Mergesort can be implemented either recursively or iteratively.
Here is the recursive mergesort algorithm:
- If the list has only one element, return the list and terminate. (Base case)
- Split the list into two halves that are as equal in length as possible. (Divide)
- Using recursion, sort both lists using mergesort. (Conquer)
- Merge the two sorted lists and return the result. (Combine)
The merge step:
- Create an empty list called the result list.
- Do the following until one of the input lists is empty: Remove the first element of the list that has a lesser first element and append it to the result list.
- When one of the lists is empty, append all elements of the other list to the result.
1 | def merge_sort(lst): |
Bubble Sort
Bubble sort is a simple, inefficient sorting algorithm used to sort lists. The Bubble sort algorithm compares each pair of elements in an array and swaps them if they are out of order until the entire array is sorted. For each element in the list, the algorithm compares every pair of elements.
The bubble sort algorithm is as follows:
- Compare A[0] and A[1]. If A[0] is bigger than A[1], swap the elements.
- Move to the next element, A[1] (which might now contain the result of a swap from the previous step), and compare it with A[2]. If A[1] is bigger than A[2], swap the elements. Do this for every pair of elements until the end of the list.
- Do steps 1 and 2 n times.
1 | def bubble_sort(lst): |
Selection Sort
The selection sort algorithm sorts an array by repeatedly finding the minimum element (considering ascending order) from unsorted part and putting it at the beginning. The algorithm maintains two subarrays in a given array. 1. The subarray which is already sorted. 2. Remaining subarray which is unsorted. In every iteration of selection sort, the minimum element (considering ascending order) from the unsorted subarray is picked and moved to the sorted subarray.
We perform the steps given below until the unsorted subarray becomes empty:
- Pick the minimum element from the unsorted subarray.
- Swap it with the leftmost element of the unsorted subarray.
- Now the leftmost element of unsorted subarray becomes a part (rightmost) of sorted subarray and will not be a part of unsorted subarray.
1 | def bubble_sort(lst): |
Quick Sort
Quicksort uses divide and conquer to sort an array. Divide and conquer is a technique used for breaking algorithms down into subproblems, solving the subproblems, and then combining the results back together to solve the original problem. It can be helpful to think of this method as divide, conquer, and combine. Divide:
- Pick a pivot element, A[q].
- Partition, or rearrange, the array into two subarrays: A[p,…,q−1] such that all elements are less than A[q], and A[q+1,…,r] such that all elements are greater than or equal to A[q].
- Conquer: Sort the subarrays A[p,…,q−1] and A[q+1,…,r] recursively with quicksort.
- Combine: No work is needed to combine the arrays because they are already sorted.
Here is a recursive algorithm for quicksort:
- If the list is empty, return the list and terminate. (Base case)
- Choose a pivot element in the list.
- Take all of the elements that are less than or equal to the pivot and use quicksort on them. (skip pivot, otherwise [5, 5, 5] will not reach base case)
- Take all of the elements that are greater than the pivot and use quicksort on them.
- Return the concatenation of the quicksorted list of elements that are less than or equal to the pivot, the pivot, and the quicksorted list of elements that are greater than the pivot.
1 | def quick_sort(lst): |
Heap Sort
Recall that, a root of the max heap is the maximum item in the array \(A[1 ... A.heap\_size]\). if we do a build_max_heap on entire \(A\), swap \(A[1]\) with \(A[n]\) and then do a max_heapify(A[1 ... n - 1], i), we end up with a sorted array.
For more detail please see Heaps
1 | def heap_sort(A): |
Reference
https://lamfo-unb.github.io/2019/04/21/Sorting-algorithms/
https://brilliant.org/wiki/sorting-algorithms/#sorting-algorithms