Insertion Sort by Swapping Elements
Insertion Sort is suitable for arrays of small size. It also achieves the best-case complexity of O(n) if the arrays are already sorted. We have discussed both Iterative Insertion Sort and Recursive Insertion Sort. In this article, slightly different implementations for both iterative and recursive versions are discussed.
Iterative Insertion Sort:
Let us look at the algorithm for the iterative insertion sort
function insertionSort(V)
i, j, k
for i from 1..length(V)
k = V[i]
j = i-1
while j > 0 and k < V[j]
V[j+1] = V[j]
j -= 1
V[j] = k
return V
Inside the while loop, we shift all values larger than k by one position and then insert k into the first position where k is larger than the array value. The same effect is obtained if we swap consecutive array elements. By repeated swapping, k will travel to its correct position.
Let’s take an example to illustrate this
Insert 3 in A = {1, 2, 4, 5, 6}
Put 3 at the end of list.
A = {1, 2, 4, 5, 6, 3}
3 < 6, swap 3 and 6
A = {1, 2, 4, 5, 3, 6}
3 < 5 swap 3 and 5
A = {1, 2, 4, 3, 5, 6}
3 < 4 swap 3 and 4
A = {1, 2, 3, 4, 5, 6}
3 > 2 so stop
By repeatedly swapping 3 travels to its proper position in the list
Therefore the above algorithm can be modified as
function insertionSort(V)
for i in 1...length(V)
j = i
while ( j > 0 and V[j] < V[j-1])
Swap V[j] and V[j-1]
j -= 1
return V
The CPP code for this algorithm is given below
Implementation:
C++
#include <iostream>
#include <vector>
using namespace std;
using Vector = vector< int >;
void printVector( const Vector& V)
{
for ( auto e : V) {
cout << e << " " ;
}
cout << endl;
}
void insertionSort(Vector& V)
{
int N = V.size();
int i, j, key;
for (i = 1; i < N; i++) {
j = i;
while (j > 0 and V[j] < V[j - 1]) {
swap(V[j], V[j - 1]);
j -= 1;
}
}
}
int main()
{
Vector A = { 9, 8, 7, 5, 2, 1, 2, 3 };
cout << "Array: " << endl;
printVector(A);
cout << "After Sorting :" << endl;
insertionSort(A);
printVector(A);
return 0;
}
|
Java
import java.io.*;
import java.util.*;
class GFG
{
static void printVector( Vector<Integer> V)
{
for ( int i = 0 ; i < V.size(); i++) {
System.out.print(V.get(i)+ " " );
}
System.out.println();
}
static void insertionSort(Vector<Integer> V)
{
int N = V.size();
int i, j, key;
for (i = 1 ; i < N; i++) {
j = i;
while (j > 0 && V.get(j) < V.get(j - 1 )) {
int temp= V.get(j);
V.set(j, V.get(j - 1 ));
V.set(j - 1 , temp);
j -= 1 ;
}
}
}
public static void main (String[] args)
{
Vector<Integer> A = new Vector<Integer> ();
A.add( 0 , 9 );
A.add( 1 , 8 );
A.add( 2 , 7 );
A.add( 3 , 5 );
A.add( 4 , 2 );
A.add( 5 , 1 );
A.add( 6 , 2 );
A.add( 7 , 3 );
System.out.print( "Array: " );
printVector(A);
System.out.print( "After Sorting :" );
insertionSort(A);
printVector(A);
}
}
|
Python3
import math
def printVector( V):
for i in V:
print (i ,end = " " )
print ( " " )
def insertionSort( V):
N = len (V)
for i in range ( 1 ,N):
j = i
while (j > 0 and V[j] < V[j - 1 ]) :
temp = V[j];
V[j] = V[j - 1 ];
V[j - 1 ] = temp;
j - = 1
A = [ 9 , 8 , 7 , 5 , 2 , 1 , 2 , 3 ]
n = len (A)
print ( "Array" )
printVector(A)
print ( "After Sorting :" )
insertionSort(A)
printVector(A)
|
C#
using System;
using System.Collections.Generic;
class GFG
{
static void printVector(List< int > V)
{
for ( int i = 0; i < V.Count; i++)
{
Console.Write(V[i] + " " );
}
Console.WriteLine();
}
static void insertionSort(List< int > V)
{
int N = V.Count;
int i, j;
for (i = 1; i < N; i++)
{
j = i;
while (j > 0 && V[j] < V[j - 1])
{
int temp= V[j];
V[j] = V[j - 1];
V[j - 1] = temp;
j -= 1;
}
}
}
public static void Main (String[] args)
{
List< int > A = new List< int > ();
A.Insert(0, 9);
A.Insert(1, 8);
A.Insert(2, 7);
A.Insert(3, 5);
A.Insert(4, 2);
A.Insert(5, 1);
A.Insert(6, 2);
A.Insert(7, 3);
Console.Write( "Array: \n" );
printVector(A);
Console.Write( "After Sorting :\n" );
insertionSort(A);
printVector(A);
}
}
|
Javascript
<script>
function printVector(V) {
for (let e of V) {
document.write(e + " " );
}
document.write( "<br>" );
}
function insertionSort(V) {
let N = V.length;
let i, j, key;
for (i = 1; i < N; i++) {
j = i;
while (j > 0 && V[j] < V[j - 1]) {
let temp = V[j];
V[j] = V[j - 1];
V[j - 1] = temp;
j -= 1;
}
}
}
let A = [9, 8, 7, 5, 2, 1, 2, 3];
document.write( "Array: " + "<br>" );
printVector(A);
document.write( "After Sorting :" + "<br>" );
insertionSort(A);
printVector(A);
</script>
|
Output
Array:
9 8 7 5 2 1 2 3
After Sorting :
1 2 2 3 5 7 8 9
Time Complexity: O(N*N)
Auxiliary Space: O(1)
Recursive Insertion Sort:
Consider an Array A of size N
- First recursively sort the sublist of A which is of size N-1
- Insert the last element of A into the sorted sublist.
To perform the insertion step use repeated swapping as discussed above.
Algorithm:
function insertionSortRecursive(A, N)
if N >= 1
insertionSortRecursive(A, N-1)
j = N-1
while j > 0 and A[j] < A[j-1]
Swap A[j] and A[j-1]
j = j-1
[end of while]
[end of if]
Following is the implementation of the above approach:
C++
#include <iostream>
#include <vector>
using namespace std;
using Vector = vector< int >;
void printVector( const Vector& V)
{
for ( auto e : V) {
cout << e << " " ;
}
cout << endl;
}
void insertionSortRecursive(Vector& V, int N)
{
if (N <= 1)
return ;
insertionSortRecursive(V, N - 1);
int j = N - 1;
while (j > 0 and V[j] < V[j - 1]) {
swap(V[j], V[j - 1]);
j -= 1;
}
}
int main()
{
Vector A = { 9, 8, 7, 5, 2, 1, 2, 3 };
cout << "Array: " << endl;
printVector(A);
cout << "After Sorting :" << endl;
insertionSortRecursive(A, A.size());
printVector(A);
return 0;
}
|
Java
import java.io.*;
import java.util.*;
class GFG
{
static void printVector( Vector<Integer> V)
{
for ( int i = 0 ; i < V.size(); i++) {
System.out.print(V.get(i) + " " );
}
System.out.println();
}
static void insertionSortRecursive(Vector<Integer> V, int N)
{
if (N <= 1 )
return ;
insertionSortRecursive(V, N - 1 );
int j = N - 1 ;
while (j > 0 && V.get(j) < V.get(j - 1 ))
{
int temp= V.get(j);
V.set(j, V.get(j - 1 ));
V.set(j - 1 , temp);
j -= 1 ;
}
}
public static void main (String[] args)
{
Vector<Integer> A = new Vector<Integer> ();
A.add( 0 , 9 );
A.add( 1 , 8 );
A.add( 2 , 7 );
A.add( 3 , 5 );
A.add( 4 , 2 );
A.add( 5 , 1 );
A.add( 6 , 2 );
A.add( 7 , 3 );
System.out.print( "Array: " );
printVector(A);
System.out.print( "After Sorting :" );
insertionSortRecursive(A,A.size());
printVector(A);
}
}
|
Python3
import math
def printVector( V):
for i in V:
print (i, end = " " )
print ( " " )
def insertionSortRecursive(V, N):
if (N < = 1 ):
return 0
insertionSortRecursive(V, N - 1 )
j = N - 1
while (j > 0 and V[j] < V[j - 1 ]) :
temp = V[j];
V[j] = V[j - 1 ];
V[j - 1 ] = temp;
j - = 1
A = [ 9 , 8 , 7 , 5 , 2 , 1 , 2 , 3 ]
n = len (A)
print ( "Array" )
printVector(A)
print ( "After Sorting :" )
insertionSortRecursive(A,n)
printVector(A)
|
C#
using System;
using System.Collections.Generic;
class GFG
{
static void printVector(List< int > V)
{
for ( int i = 0; i < V.Count; i++)
{
Console.Write(V[i] + " " );
}
Console.WriteLine();
}
static void insertionSortRecursive(List< int > V,
int N)
{
if (N <= 1)
return ;
insertionSortRecursive(V, N - 1);
int j = N - 1;
while (j > 0 && V[j] < V[j - 1])
{
int temp = V[j];
V[j] = V[j - 1];
V[j - 1] = temp;
j -= 1;
}
}
public static void Main (String[] args)
{
List< int > A = new List< int > ();
A.Insert(0, 9);
A.Insert(1, 8);
A.Insert(2, 7);
A.Insert(3, 5);
A.Insert(4, 2);
A.Insert(5, 1);
A.Insert(6, 2);
A.Insert(7, 3);
Console.Write( "Array: " );
printVector(A);
Console.Write( "After Sorting :" );
insertionSortRecursive(A, A.Count);
printVector(A);
}
}
|
Javascript
<script>
function printVector(V) {
for (let e of V) {
document.write(e + " " );
}
document.write( "<br>" );
}
function insertionSortRecursive(V, N) {
if (N <= 1)
return ;
insertionSortRecursive(V, N - 1);
let j = N - 1;
while (j > 0 && V[j] < V[j - 1]) {
let temp = V[j];
V[j] = V[j - 1];
V[j - 1] = temp;
j -= 1;
}
}
let A = [9, 8, 7, 5, 2, 1, 2, 3];
document.write( "Array: <br>" );
printVector(A);
document.write( "After Sorting :<br>" );
insertionSortRecursive(A, A.length);
printVector(A);
</script>
|
Output
Array:
9 8 7 5 2 1 2 3
After Sorting :
1 2 2 3 5 7 8 9
Note: The Time Complexity of the algorithm is still O(N^2) in the worst case. Moreover, these versions are potentially slower since repeated swapping requires more operations. However, these versions are discussed because of their implementation simplicity and ease of understanding.
Last Updated :
22 Dec, 2022
Like Article
Save Article
Share your thoughts in the comments
Please Login to comment...