Given an array arr[ ] of n integers. The task is to find the first greater element for every array element in the array using upper_bound( ) function. If there is no greater element possible for any array element return -1.
Examples :
Input: n = 7, arr[ ] = {4, 7, 3, 1, 3, 2, 5}
Output: 7 -1 4 4 4 4 7
Explanation : First greater element for first, third, fourth, fifth, sixth and last element are 7, 4, 4, 4, 4, and 7 . Second element of arr[ ] do not have it’s first greater element of itself.
Input : n = 4, arr[ ] = {2, 8, 8, 1}
Output : 8 -1 -1 2
Explanation : First greater element for first and last element are 8 and 2 . Second and third element of arr[ ] do not have it’s first greater element of itself .
Naive Approach: The Naive Approach and the stack approach are discussed in Set 1 of this article. Here, we have discussed the method to solve it using upper_bound().
Approach: Since upper_bound( ) cannot be applied in an unsorted array. The idea is to try to modify the array so that it becomes sorted. Thus, create an array let’s name it copy[], which will have its elements in a sorted manner. First initialize copy[ ] with 0 and update every element of copy [ ] as : copy[i] = max(copy[i-1], arr[i]). Now, upper_bound( ) can be applied in the copy [ ] and find first greater element for every arr[i]. Follow the steps below to solve the problem:
- Initialize an array copy[n] with values 0.
- Iterate over the range [1, n) using the variable i and perform the following steps:
- Set the value of copy[i] as the maximum of copy[i-1] or arr[i].
- Iterate over the range [0, n) using the variable i and perform the following steps:
- Initialize the variable high as the upper bound of arr[i] in the copy[] array.
- If high equals n then print -1 otherwise print arr[high].
Below is the implementation of the above approach:
C++
#include <bits/stdc++.h>
using namespace std;
void FirstGreater( int arr[], int n)
{
int copy[n];
memset (copy, 0, sizeof (copy));
copy[0] = arr[0];
for ( int i = 1; i < n; i++) {
copy[i] = max(copy[i - 1], arr[i]);
}
for ( int i = 0; i < n; i++) {
int high
= upper_bound(copy,
copy + n, arr[i])
- copy;
if (high == n) {
cout << "-1"
<< " " ;
}
else {
cout << arr[high] << " " ;
}
}
}
int main()
{
int arr[] = { 4, 7, 3, 1, 3, 2, 5 };
int n = sizeof (arr) / sizeof (arr[0]);
FirstGreater(arr, n);
return 0;
}
|
Java
import java.io.*;
class GFG {
static int upper_bound( int arr[], int N, int X)
{
int mid;
int low = 0 ;
int high = N;
while (low < high)
{
mid = low + (high - low) / 2 ;
if (X >= arr[mid]) {
low = mid + 1 ;
}
else {
high = mid;
}
}
if (low < N && arr[low] <= X) {
low++;
}
return low;
}
static void FirstGreater( int arr[], int n)
{
int copy[] = new int [n];
copy[ 0 ] = arr[ 0 ];
for ( int i = 1 ; i < n; i++)
{
copy[i] = Math.max(copy[i - 1 ], arr[i]);
}
for ( int i = 0 ; i < n; i++)
{
int high
= upper_bound(copy, copy.length, arr[i]);
if (high == n) {
System.out.print( "-1"
+ " " );
}
else {
System.out.print(arr[high] + " " );
}
}
}
public static void main(String[] args)
{
int arr[] = { 4 , 7 , 3 , 1 , 3 , 2 , 5 };
int n = arr.length;
FirstGreater(arr, n);
}
}
|
Python3
import bisect
def FirstGreater(arr, n):
copy = [ 0 ] * n
copy[ 0 ] = arr[ 0 ]
for i in range ( 1 , n):
copy[i] = max (copy[i - 1 ], arr[i])
for i in range (n):
high = bisect.bisect_right(copy, arr[i], 0 , n)
if (high = = n):
print ( "-1" , end = " " )
else :
print (arr[high], end = " " )
if __name__ = = "__main__" :
arr = [ 4 , 7 , 3 , 1 , 3 , 2 , 5 ]
n = len (arr)
FirstGreater(arr, n)
|
C#
using System;
public class GFG
{
static int upper_bound( int []arr, int N, int X)
{
int mid;
int low = 0;
int high = N;
while (low < high)
{
mid = low + (high - low) / 2;
if (X >= arr[mid]) {
low = mid + 1;
}
else {
high = mid;
}
}
if (low < N && arr[low] <= X) {
low++;
}
return low;
}
static void FirstGreater( int []arr, int n)
{
int []copy = new int [n];
copy[0] = arr[0];
for ( int i = 1; i < n; i++)
{
copy[i] = Math.Max(copy[i - 1], arr[i]);
}
for ( int i = 0; i < n; i++)
{
int high
= upper_bound(copy, copy.Length, arr[i]);
if (high == n) {
Console.Write( "-1"
+ " " );
}
else {
Console.Write(arr[high] + " " );
}
}
}
public static void Main(String[] args)
{
int []arr = { 4, 7, 3, 1, 3, 2, 5 };
int n = arr.Length;
FirstGreater(arr, n);
}
}
|
Javascript
<script>
function FirstGreater(arr, n) {
let copy = new Array(n);
copy.fill(0)
copy[0] = arr[0];
for (let i = 1; i < n; i++) {
copy[i] = Math.max(copy[i - 1], arr[i]);
}
for (let i = 0; i < n; i++) {
let high = upper_bound(copy, 0, copy.length - 1, arr[i]);
if (high == n) {
document.write( "-1 " );
}
else {
document.write(arr[high] + " " );
}
}
}
function upper_bound(arr, low, high, X) {
if (low > high)
return low;
let mid = Math.floor(low + (high - low) / 2);
if (arr[mid] <= X) {
return upper_bound(arr, mid + 1,
high, X);
}
return upper_bound(arr, low,
mid - 1, X);
}
let arr = [4, 7, 3, 1, 3, 2, 5];
let n = arr.length
FirstGreater(arr, n);
</script>
|
Time Complexity: O(n*log(n))
Auxiliary Space: O(n)