Given an integer array where the two parts around a break point are individually sorted, merge them into a single sorted array. The break point can be anywhere in the array, including at the beginning or end.
Examples:
Input: arr[] = [2, 3, 8, -1, 7, 10]
Output: [-1, 2, 3, 7, 8, 10]
Explanation: [2, 3, 8] and [-1, 7, 10] are sorted in the original array. The overall sorted version is [-1 2 3 7 8 10]Input: arr[] = [-4, 6, 9, -1, 3]
Output: [-4, -1, 3, 6, 9]
Explanation: [-4, 6, 9] and [-1, 3] are sorted in the original array. The overall sorted version is [-4 -1 3 6 9]Input: arr[] = [10, 20, 30]
Output: [10, 20, 30]
Explanation: One part is empty and the other part is whole array which is already sorted.
Table of Content
[Naive Approach] Sort the array
The main logic is to sort the array using built in functions (generally an implementation of quick sort). This approach ignores the “two parts” and simply calls the language’s built‑in sort to sort the entire array.
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
void mergeTwoParts(vector<int> &arr){
// Sort the given array using sort STL
sort(arr.begin(), arr.end());
}
int main(){
vector<int> arr = {2, 3, 8, -1, 7, 10};
int n = arr.size();
mergeTwoParts(arr);
for (int i = 0; i < n; i++)
cout << arr[i] << " ";
return 0;
}
import java.util.Arrays;
public class Main {
public static void mergeTwoParts(int[] arr) {
// Sort the given array using sort STL
Arrays.sort(arr);
}
public static void main(String[] args) {
int[] arr = {2, 3, 8, -1, 7, 10};
mergeTwoParts(arr);
for (int i = 0; i < arr.length; i++)
System.out.print(arr[i] + " ");
}
}
def mergeTwoParts(arr):
# Sort the given list using list.sort()
arr.sort()
if __name__ == "__main__":
arr = [2, 3, 8, -1, 7, 10]
n = len(arr)
mergeTwoParts(arr)
for i in range(n):
print(arr[i], end=" ")
using System;
using System.Linq;
public class Program {
public static void mergeTwoParts(int[] arr) {
// Sort the given array using sort STL
Array.Sort(arr);
}
public static void Main() {
int[] arr = {2, 3, 8, -1, 7, 10};
mergeTwoParts(arr);
for (int i = 0; i < arr.Length; i++)
Console.Write(arr[i] + " ");
}
}
function mergeTwoParts(arr)
{
// Sort the given array using Array.prototype.sort
arr.sort((a, b) => a - b);
}
// Driver Code
const arr = [ 2, 3, 8, -1, 7, 10 ];
const n = arr.length;
mergeTwoParts(arr);
for (let i = 0; i < n; i++)
process.stdout.write(arr[i] + " ");
Output
-1 2 3 7 8 10
Time Complexity : O(n(log(n)))
Auxiliary Space : O(log(n))
Note :- For Java, Python and C# the Space Complexity will be O(n)
[Expected Approach] Using merge sort - O(n) Time and O(n) Space
The main idea is to use an auxiliary array which is very similar to the Merge Function of Merge sort.
Find where the first sorted part ends, then walk through both parts side by side, always picking the smaller next number to build the fully sorted list.
#include <iostream>
#include <vector>
using namespace std;
void mergeTwoParts(vector<int> &arr){
int n = arr.size();
// starting index of second half
int index = 0;
// Temp Array store sorted resultant array
vector<int> temp(n);
// First Find the point where array is divided
// into two half
for (int i = 0; i < n - 1; i++) {
if (arr[i] > arr[i + 1]) {
index = i + 1;
break;
}
}
// If Given array is all-ready sorted
if (index == 0)
return;
// Merge two sorted arrays in single sorted array
int i = 0, j = index, k = 0;
while (i < index && j < n) {
if (arr[i] < arr[j])
temp[k++] = arr[i++];
else
temp[k++] = arr[j++];
}
// Copy the remaining elements of arr[i to index ]
while (i < index)
temp[k++] = arr[i++];
// Copy the remaining elements of arr[index to n ]
while (j < n)
temp[k++] = arr[j++];
for (int i = 0; i < n; i++) {
arr[i] = temp[i];
}
}
int main(){
vector<int> arr = {2, 3, 8, -1, 7, 10};
int n = arr.size();
mergeTwoParts(arr);
for (int i = 0; i < n; i++)
cout << arr[i] << " ";
return 0;
}
import java.util.ArrayList;
class GFG {
public static void mergeTwoParts(int[] arr) {
int n = arr.length;
// starting index of second half
int index= 0;
// Temp Array store sorted resultant array
ArrayList<Integer> temp = new ArrayList<>();
for (int i = 0; i < n; i++) temp.add(0);
// First Find the point where array is divided
// into two half
for (int i = 0; i < n - 1; i++) {
if (arr[i] > arr[i + 1]) {
index = i + 1;
break;
}
}
// If Given array is all-ready sorted
if (index == 0) {
ArrayList<Integer> original = new ArrayList<>();
for (int x : arr) original.add(x);
for (int i = 0; i < n; i++) arr[i] = original.get(i);
return;
}
// Merge two sorted arrays in single sorted array
int i = 0, j = index, k = 0;
while (i < index && j < n) {
if (arr[i] < arr[j])
temp.set(k++, arr[i++]);
else
temp.set(k++, arr[j++]);
}
// Copy the remaining elements of arr[i to index ]
while (i < index)
temp.set(k++, arr[i++]);
// Copy the remaining elements of arr[index to n ]
while (j < n)
temp.set(k++, arr[j++]);
for (int x = 0; x < n; x++) arr[x] = temp.get(x);
}
public static void main(String[] args) {
int[] arr = {2, 3, 8, -1, 7, 10};
int n = arr.length;
mergeTwoParts(arr);
for (int i = 0; i < n; i++) {
System.out.print(arr[i] + " ");
}
}
}
def mergeTwoParts(arr):
n = len(arr)
# starting index of second half
index = 0
# Temp Array store sorted resultant array
temp = [0] * n
# First Find the point where array is divided
# into two half
for i in range(n - 1):
if arr[i] > arr[i + 1]:
index = i + 1
break
# If Given array is all-ready sorted
if index == 0:
return
# Merge two sorted arrays in single sorted array
i, j, k = 0, index, 0
while i < index and j < n:
if arr[i] < arr[j]:
temp[k] = arr[i]
i += 1
else:
temp[k] = arr[j]
j += 1
k += 1
# Copy the remaining elements of arr[i to index]
while i < index:
temp[k] = arr[i]
i += 1
k += 1
# Copy the remaining elements of arr[index to n ]
while j < n:
temp[k] = arr[j]
j += 1
k += 1
for i in range(n):
arr[i] = temp[i]
if __name__ == "__main__":
arr = [2, 3, 8, -1, 7, 10]
n = len(arr)
mergeTwoParts(arr)
for i in range(n):
print(arr[i], end=" ")
using System;
using System.Collections.Generic;
public class GFG {
public static void mergeTwoParts(int[] arr) {
int n = arr.Length;
// starting index of second half
int index = 0;
// Temp Array store sorted resultant array
List<int> temp = new List<int>(new int[n]);
// First Find the point where array is divided
// into two half
for (int i = 0; i < n - 1; i++) {
if (arr[i] > arr[i + 1]) {
index = i + 1;
break;
}
}
// If Given array is all-ready sorted
if (index == 0) {
// copy original array into a List to return
List<int> original = new List<int>();
foreach (int x in arr) original.Add(x);
arr = original.ToArray();
return;
}
// Merge two sorted arrays in single sorted array
int i1 = 0, j = index, k = 0;
while (i1 < index && j < n) {
if (arr[i1] < arr[j])
temp[k++] = arr[i1++];
else
temp[k++] = arr[j++];
}
// Copy the remaining elements of arr[i to index ]
while (i1 < index)
temp[k++] = arr[i1++];
// Copy the remaining elements of arr[ index to n ]
while (j < n)
temp[k++] = arr[j++];
for (int i = 0; i < n; i++) {
arr[i] = temp[i];
}
}
public static void Main() {
int[] arr = {2, 3, 8, -1, 7, 10};
int n = arr.Length;
mergeTwoParts(arr);
for (int i = 0; i < n; i++)
Console.Write(arr[i] + " ");
}
}
function mergeTwoParts(arr) {
let n = arr.length;
// starting index of second half
let index = 0;
// Temp Array store sorted resultant array
let temp = new Array(n).fill(0);
// First Find the point where array is divided
// into two half
for (let i = 0; i < n - 1; i++) {
if (arr[i] > arr[i + 1]) {
index = i + 1;
break;
}
}
// If Given array is all-ready sorted
if (index === 0) {
for (let i = 0; i < n; i++) {
temp[i] = arr[i];
}
} else {
// Merge two sorted arrays in single sorted array
let i = 0, j = index, k = 0;
while (i < index && j < n) {
if (arr[i] < arr[j])
temp[k++] = arr[i++];
else
temp[k++] = arr[j++];
}
// Copy the remaining elements of arr[i to index ]
while (i < index)
temp[k++] = arr[i++];
// Copy the remaining elements of arr[ index to n ]
while (j < n)
temp[k++] = arr[j++];
}
// Modify arr[] with the sorted temp[] array
for (let i = 0; i < n; i++) {
arr[i] = temp[i];
}
}
// Driver Code
let arr = [2, 3, 8, -1, 7, 10];
let n = arr.length;
mergeTwoParts(arr);
for (let i = 0; i < n; i++) {
process.stdout.write(arr[i] + " ");
}
Output
-1 2 3 7 8 10