k smallest elements in same order using O(1) extra space


We have an array "nums" consisting of "size" elements and an integer "number" denoting the number of smallest elements we have to return. Our task is to find out the "number" smallest elements from the given array. The order of the elements should be preserved and we are not allowed to use any extra variable space for the solution i.e., the space complexity of the solution should be O(1).

Let us understand this using an example,

nums = { 4, 2, 6, 5, 1 }

The solution should return 4, 2, 5 as they are the smallest 3 elements of the given array. One thing is also noticeable that the order of the numbers output is 4, 2, 5 and not 2, 4, 5 hence the original order of the numbers is maintained.

The output should be −

The smallest 3 elements of the given array are

4 2 1

Approach 1

The idea behind the algorithm is to move the k minimum elements to the beginning of the array while maintaining their original order. To achieve this, a modified version of the insertion sort algorithm can be used.

Here is a step-by-step explanation of the algorithm −

  • Start by iterating from the ('number' +1)th element to the end of the array.

  • For each element encountered in the iteration, compare it with the largest element among the first 'number' elements.

  • If the current element is smaller than the largest element among the first k elements, replace the largest element with the current element.

  • To maintain the order of the elements, perform the replacement by shifting all the elements from the first 'number' elements one position to the right, discarding the previous largest element.

  • Continue the iteration until the end of the array.

Example

The implementation of the solution discussed above in C++ is given below −

#include <iostream>
#include<bits/stdc++.h>
using namespace std;
void smallest_three(int nums[], int size, int number){
   for (int iterator = number; iterator < size; ++iterator){
      int largesr_number = nums[number - 1];
      int pos = number - 1;
      for (int iterator_2 = number - 2; iterator_2 >= 0; iterator_2--){
         if (nums[iterator_2] > largesr_number){
            largesr_number = nums[iterator_2];
            pos = iterator_2;
         }
      }
      if (largesr_number > nums[iterator]){
         int iterator_2 = pos;
         while (iterator_2 < number - 1){
            nums[iterator_2] = nums[iterator_2 + 1];
            iterator_2++;
         }
         nums[number - 1] = nums[iterator];
      }
   }	
   for (int iterator = 0; iterator < number; iterator++){
      cout << nums[iterator] << " ";
   }
}
int main(){
   int nums[] = { 4, 2, 6, 5, 1 };
   int size = sizeof(nums) / sizeof(nums[0]);
   int number = 3;
   cout<< "The smallest " << number << " elements " << "of the given array are " <<endl;
   smallest_three(nums, size, number);
   return 0;
}

Output

The smallest 3 elements of the given array are 
4 2 1
  • Time complexity − The time complexity of the code implemented above is O(n^2) as we are using two nested loops.

  • Space complexity − As we were asked to not use any variable extra space in the code, the space complexity of this is O(1).

Updated on: 05-Oct-2023

44 Views

Kickstart Your Career

Get certified by completing the course

Get Started
Advertisements