给定数组arr [] ,任务是找到使数组递减所需的最少步骤,其中在每个步骤中删除所有大于其左侧元素的元素。
例子:
Input: arr[] = {3, 2, 1, 7, 5}
Output: 2
Explanation:
In the above array there are two steps required to make array decreasing –
Step 1: In step 1 there is one element which is greater than its left, that is 7 > 1.
Step 2: In step 2 there is one element which is greater than its left, that is 5 > 1.
Input: arr[] = {6, 5, 8, 4, 7, 10, 9}
Output: 2
In the above array there are two steps required to make array decreasing –
Step 1: In step 1 there are three elements which is greater than its left, which is 8 > 5, 7 > 4 and 10 > 7.
Step 2: In step 2 there are three is only one element which is greater than its left which is 9 > 4.
天真的方法:遍历数组并计算大于其左侧的元素,如果该元素不大于其左侧,则将其推入另一个数组(例如arr1 ),并在该数组完全迭代后复制所有元素将arr1的值赋给初始数组,然后重复相同的过程,直到在步骤中删除的元素计数为0为止。这种方法在最坏的情况下需要O(N 2 )时间,在O(N)空间中也需要花费时间。
高效的方法:想法是使用一个堆栈,并且仅当该元素大于其先前的元素时才将其推入堆栈,否则计算扫描和弹出的次数。
我们只关心较小的元素。
CPP
//C++ implementation to make an
// array decreasing
#include
using namespace std;
// Structure to store elements
struct Node
{
int elementID;
int stepsToeliminate;
};
// Function to find the
// minimum steps required
void minSteps(int arr[], int N)
{
stack s;
s.push({ 0, -1 });
// Minimum steps
int maxStepsToeliminate = -1;
// Loop to iterate
// over the array
for (int i = 1; i < N; i++)
{
int stepsToeliminate = 1;
// Traversing the stack until
// it is not empty
while (!s.empty())
{
// Condition if the top of the
// stack is greater than the
// current element
if (arr[s.top().elementID] >=
arr[i])
{
stepsToeliminate = max(stepsToeliminate,
s.top().stepsToeliminate + 1);
s.pop();
}
else
{
break;
}
}
// Condition if no previous
// elements value less than
// this element then steps is -1
if (s.empty())
{
stepsToeliminate = -1;
}
maxStepsToeliminate = max(
maxStepsToeliminate, stepsToeliminate
);
s.push({ i, stepsToeliminate });
}
cout << (maxStepsToeliminate < 0 ? 0 :
maxStepsToeliminate) << endl;
}
// Driver Code
int main()
{
int arr[] = {3, 2, 1, 7, 5};
int size = sizeof(arr)/sizeof(arr[0]);
minSteps(arr, size);
return 0;
}
Java
// Java implementation to make an
// array decreasing
import java.util.*;
class GFG{
// Structure to store elements
static class Node
{
int elementID;
int stepsToeliminate;
public Node(int elementID, int stepsToeliminate) {
super();
this.elementID = elementID;
this.stepsToeliminate = stepsToeliminate;
}
};
// Function to find the
// minimum steps required
static void minSteps(int arr[], int N)
{
Stack s = new Stack();
s.add(new Node( 0, -1 ));
// Minimum steps
int maxStepsToeliminate = -1;
// Loop to iterate
// over the array
for (int i = 1; i < N; i++)
{
int stepsToeliminate = 1;
// Traversing the stack until
// it is not empty
while (!s.isEmpty())
{
// Condition if the top of the
// stack is greater than the
// current element
if (arr[s.peek().elementID] >=
arr[i])
{
stepsToeliminate = Math.max(stepsToeliminate,
s.peek().stepsToeliminate + 1);
s.pop();
}
else
{
break;
}
}
// Condition if no previous
// elements value less than
// this element then steps is -1
if (s.isEmpty())
{
stepsToeliminate = -1;
}
maxStepsToeliminate = Math.max(
maxStepsToeliminate, stepsToeliminate
);
s.add(new Node(i, stepsToeliminate ));
}
System.out.print((maxStepsToeliminate < 0 ? 0 :
maxStepsToeliminate) +"\n");
}
// Driver Code
public static void main(String[] args)
{
int arr[] = {3, 2, 1, 7, 5};
int size = arr.length;
minSteps(arr, size);
}
}
// This code is contributed by sapnasingh4991
Python3
# Python3 implementation to make an
# array decreasing
# Function to find the
# minimum steps required
def minSteps(arr, N) :
s = [];
s.append(( 0, -1 ));
# Minimum steps
maxStepsToeliminate = -1;
# Loop to iterate
# over the array
for i in range(1, N) :
stepsToeliminate = 1;
# Traversing the stack until
# it is not empty
while (len(s) != 0) :
# Condition if the top of the
# stack is greater than the
# current element
if (arr[s[-1][0]] >= arr[i]) :
stepsToeliminate = max(stepsToeliminate, s[-1][1] + 1);
s.pop();
else :
break;
# Condition if no previous
# elements value less than
# this element then steps is -1
if (len(s) == 0) :
stepsToeliminate = -1;
maxStepsToeliminate = max( maxStepsToeliminate, stepsToeliminate );
s.append(( i, stepsToeliminate ));
print( 0 if (maxStepsToeliminate < 0 ) else maxStepsToeliminate );
# Driver Code
if __name__ == "__main__" :
arr = [3, 2, 1, 7, 5];
size = len(arr);
minSteps(arr, size);
# This code is contributed by AnkitRai01
C#
// C# implementation to make an
// array decreasing
using System;
using System.Collections.Generic;
class GFG{
// Structure to store elements
class Node
{
public int elementID;
public int stepsToeliminate;
public Node(int elementID, int stepsToeliminate) {
this.elementID = elementID;
this.stepsToeliminate = stepsToeliminate;
}
};
// Function to find the
// minimum steps required
static void minSteps(int []arr, int N)
{
Stack s = new Stack();
s.Push(new Node( 0, -1 ));
// Minimum steps
int maxStepsToeliminate = -1;
// Loop to iterate
// over the array
for (int i = 1; i < N; i++)
{
int stepsToeliminate = 1;
// Traversing the stack until
// it is not empty
while (s.Count!=0)
{
// Condition if the top of the
// stack is greater than the
// current element
if (arr[s.Peek().elementID] >=
arr[i])
{
stepsToeliminate = Math.Max(stepsToeliminate,
s.Peek().stepsToeliminate + 1);
s.Pop();
}
else
{
break;
}
}
// Condition if no previous
// elements value less than
// this element then steps is -1
if (s.Count!=0)
{
stepsToeliminate = -1;
}
maxStepsToeliminate = Math.Max(
maxStepsToeliminate, stepsToeliminate
);
s.Push(new Node(i, stepsToeliminate ));
}
Console.Write((maxStepsToeliminate < 0 ? 0 :
maxStepsToeliminate) +"\n");
}
// Driver Code
public static void Main(String[] args)
{
int []arr = {3, 2, 1, 7, 5};
int size = arr.Length;
minSteps(arr, size);
}
}
// This code is contributed by PrinciRaj1992
2
性能分析:
- 时间复杂度:与上述方法一样,有一个循环占用O(N)时间,因此时间复杂度将为O(N) 。
- 空间复杂度:与上述方法一样,这里使用堆栈来存储先前的元素,因此空间复杂度将为O(N) 。