打印下一个更大数量的 Q 查询
给定一个包含 n 个元素和 q 个查询的数组,对于每个索引为 i 的查询,找到下一个更大的元素并打印它的值。如果它的右边没有更大的元素,则打印-1。
例子:
Input : arr[] = {3, 4, 2, 7, 5, 8, 10, 6}
query indexes = {3, 6, 1}
Output: 8 -1 7
Explanation :
For the 1st query index is 3, element is 7 and
the next greater element at its right is 8
For the 2nd query index is 6, element is 10 and
there is no element greater then 10 at right,
so print -1.
For the 3rd query index is 1, element is 4 and
the next greater element at its right is 7.
正常方法:正常方法是让每个查询在循环中从索引移动到 n 并找出下一个更大的元素并打印它,但在最坏的情况下这将需要 n 次迭代,如果查询的数量很多很高。
时间复杂度:O(n^2)
辅助空间>:O(1)
有效的方法:
一种有效的方法是基于下一个更大的元素。我们将下一个更大元素的索引存储在一个数组中,并且对于每个查询过程,在O(1)中回答查询,这将提高效率。
但是要找出数组中每个索引的下一个更大的元素,有两种方法。
一个将占用o(n^2)和O(n)空间,这将从 I+1 迭代到 n 索引 I 处的每个元素,并找出下一个更大的元素并存储它。
但更有效的方法是使用堆栈,我们使用索引来比较并在 next[] 中存储下一个更大的元素索引。
1)将第一个索引压入堆栈。
2)一一选择其余索引,然后循环执行以下步骤。
....a) 将当前元素标记为 i。
....b) 如果堆栈不为空,则从堆栈中弹出一个索引并将 a[index] 与 a[I] 进行比较。
....c) 如果 a[I] 大于 a[index],则 a[I] 是 a[index] 的下一个更大元素。
....d) 当弹出的索引元素小于 a[I] 时,继续从堆栈中弹出。 a[I] 成为所有此类弹出元素的下一个更大元素
....g) 如果 a[I] 小于弹出的索引元素,则将弹出的索引推回。
3) 步骤 2 中的循环结束后,从堆栈中弹出所有索引并打印 -1 作为它们的下一个索引。
C++
// C++ program to print
// next greater number
// of Q queries
#include
using namespace std;
// array to store the next
// greater element index
void next_greatest(int next[],
int a[], int n)
{
// use of stl
// stack in c++
stack s;
// push the 0th
// index to the stack
s.push(0);
// traverse in the
// loop from 1-nth index
for (int i = 1; i < n; i++)
{
// iterate till loop is empty
while (!s.empty()) {
// get the topmost
// index in the stack
int cur = s.top();
// if the current element is
// greater then the top indexth
// element, then this will be
// the next greatest index
// of the top indexth element
if (a[cur] < a[i])
{
// initialise the cur
// index position's
// next greatest as index
next[cur] = i;
// pop the cur index
// as its greater
// element has been found
s.pop();
}
// if not greater
// then break
else
break;
}
// push the i index so that its
// next greatest can be found
s.push(i);
}
// iterate for all other
// index left inside stack
while (!s.empty())
{
int cur = s.top();
// mark it as -1 as no
// element in greater
// then it in right
next[cur] = -1;
s.pop();
}
}
// answers all
// queries in O(1)
int answer_query(int a[], int next[],
int n, int index)
{
// stores the next greater
// element positions
int position = next[index];
// if position is -1 then no
// greater element is at right.
if (position == -1)
return -1;
// if there is a index that
// has greater element
// at right then return its
// value as a[position]
else
return a[position];
}
// Driver Code
int main()
{
int a[] = {3, 4, 2, 7,
5, 8, 10, 6 };
int n = sizeof(a) / sizeof(a[0]);
// initializes the
// next array as 0
int next[n] = { 0 };
// calls the function
// to pre-calculate
// the next greatest
// element indexes
next_greatest(next, a, n);
// query 1 answered
cout << answer_query(a, next, n, 3) << " ";
// query 2 answered
cout << answer_query(a, next, n, 6) << " ";
// query 3 answered
cout << answer_query(a, next, n, 1) << " ";
}
Java
// Java program to print
// next greater number
// of Q queries
import java.util.*;
class GFG
{
public static int[] query(int arr[],
int query[])
{
int ans[] = new int[arr.length];// this array contains
// the next greatest
// elements of all the elements
Stack s = new Stack<>();
// push the 0th index
// to the stack
s.push(arr[0]);
int j = 0;
//traverse rest
// of the array
for(int i = 1; i < arr.length; i++)
{
int next = arr[i];
if(!s.isEmpty())
{
// get the topmost
// element in the stack
int element = s.pop();
/* If the popped element
is smaller than next,
then a) store the pair
b) keep popping while
elements are smaller and
stack is not empty */
while(next > element)
{
ans[j] = next;
j++;
if(s.isEmpty())
break;
element = s.pop();
}
/* If element is greater
than next, then
push the element back */
if (element > next)
s.push(element);
}
/* push next to stack so
that we can find next
greater for it */
s.push(next);
}
/* After iterating over the
loop, the remaining elements
in stack do not have the next
greater element, so -1 for them */
while(!s.isEmpty())
{
int element = s.pop();
ans[j] = -1;
j++;
}
// return the next
// greatest array
return ans;
}
// Driver Code
public static void main(String[] args)
{
int arr[] = {3, 4, 2, 7,
5, 8, 10, 6};
int query[] = {3, 6, 1};
int ans[] = query(arr,query);
// getting output array
// with next greatest elements
for(int i = 0; i < query.length; i++)
{
// displaying the next greater
// element for given set of queries
System.out.print(ans[query[i]] + " ");
}
}
}
// This code was contributed
// by Harshit Sood
Python3
# Python3 program to print
# next greater number
# of Q queries
# array to store the next
# greater element index
def next_greatest(next, a, n):
# use of stl
# stack in c++
s = []
# push the 0th
# index to the stack
s.append(0);
# traverse in the
# loop from 1-nth index
for i in range(1, n):
# iterate till loop is empty
while (len(s) != 0):
# get the topmost
# index in the stack
cur = s[-1]
# if the current element is
# greater then the top indexth
# element, then this will be
# the next greatest index
# of the top indexth element
if (a[cur] < a[i]):
# initialise the cur
# index position's
# next greatest as index
next[cur] = i;
# pop the cur index
# as its greater
# element has been found
s.pop();
# if not greater
# then break
else:
break;
# push the i index so that its
# next greatest can be found
s.append(i);
# iterate for all other
# index left inside stack
while(len(s) != 0):
cur = s[-1]
# mark it as -1 as no
# element in greater
# then it in right
next[cur] = -1;
s.pop();
# answers all
# queries in O(1)
def answer_query(a, next, n, index):
# stores the next greater
# element positions
position = next[index];
# if position is -1 then no
# greater element is at right.
if(position == -1):
return -1;
# if there is a index that
# has greater element
# at right then return its
# value as a[position]
else:
return a[position];
# Driver Code
if __name__=='__main__':
a = [3, 4, 2, 7, 5, 8, 10, 6 ]
n = len(a)
# initializes the
# next array as 0
next=[0 for i in range(n)]
# calls the function
# to pre-calculate
# the next greatest
# element indexes
next_greatest(next, a, n);
# query 1 answered
print(answer_query(a, next, n, 3), end = ' ')
# query 2 answered
print(answer_query(a, next, n, 6), end = ' ')
# query 3 answered
print(answer_query(a, next, n, 1), end = ' ')
# This code is contributed by rutvik_56.
C#
// C# program to print next greater
// number of Q queries
using System;
using System.Collections.Generic;
class GFG
{
public static int[] query(int[] arr,
int[] query)
{
int[] ans = new int[arr.Length]; // this array contains
// the next greatest
// elements of all the elements
Stack s = new Stack();
// push the 0th index to the stack
s.Push(arr[0]);
int j = 0;
// traverse rest of the array
for (int i = 1; i < arr.Length; i++)
{
int next = arr[i];
if (s.Count > 0)
{
// get the topmost element in the stack
int element = s.Pop();
/* If the popped element is smaller
than next, then
a) store the pair
b) keep popping while
elements are smaller and
stack is not empty */
while (next > element)
{
ans[j] = next;
j++;
if (s.Count == 0)
{
break;
}
element = s.Pop();
}
/* If element is greater
than next, then
push the element back */
if (element > next)
{
s.Push(element);
}
}
/* push next to stack so that we
can find next greater for it */
s.Push(next);
}
/* After iterating over the
loop, the remaining elements
in stack do not have the next
greater element, so -1 for them */
while (s.Count > 0)
{
int element = s.Pop();
ans[j] = -1;
j++;
}
// return the next greatest array
return ans;
}
// Driver Code
public static void Main(string[] args)
{
int[] arr = new int[] {3, 4, 2, 7, 5, 8, 10, 6};
int[] query = new int[] {3, 6, 1};
int[] ans = GFG.query(arr, query);
// getting output array
// with next greatest elements
for (int i = 0; i < query.Length; i++)
{
// displaying the next greater
// element for given set of queries
Console.Write(ans[query[i]] + " ");
}
}
}
// This code is contributed by Shrikant13
Javascript
输出:
8 -1 7