Minimize count of peaks and troughs in given Array after at most one replacement
Last Updated :
29 Jul, 2022
Given an array arr[] containing N positive integers, the task is to minimize the total count of peaks (elements having greater value than both the neighbours) and troughs (elements having less value than both the neighbours) by replacing at most one element of the given array with any value.
Note: The first and the last element of the array cannot be a peak or trough as they don’t have two neighbours.
Examples:
Input: arr[] = {2, 7, 4}
Output: 0
Explanation: The count can be made 0 by changing 7 to 3.
The array becomes {2, 3, 4} with no trough and peak.
Input: arr[] = {1, 4, 3, 5, 3, 8}
Output: 1
Explanation: Initially the total count is 4. Go to the index 2 and change its value to 5.
Now the sequence becomes {1, 4, 5, 5, 3, 8}.
Now only one trough at index 4.
Approach: The given problem can be solved using the Greedy approach. Observe that, any change in ith index affects only the elements at (i+1)th and (i-1)th index. Follow the steps below to solve this problem:
- Initialize a boolean array mark as false.
- Also, initialize an integer variable total as 0. It keeps the track of the overall balance of the given sequence.
- Now iterate over the given array and mark its ith index as true if ith element of the array is either a peak or trough.
- Initialize another variable ans as total. It keeps the track of the final answer.
- Now iterate over the array again,
- Suppose, currently the iteration is at index i,
- Make the element at the index i equal to i + 1 and update the total balance of the array now.
- Make the element at the index i equal to i – 1 and update the total balance of the array now.
- The total balance for the above cases can be achieved easily by creating function isUp() and isDown() that checks there is a peak and trough respectively at a particular index.
- Also, update the ans variable accordingly.
- Print the value represented by ans variable.
Below is the implementation of the above approach:
C++
#include <bits/stdc++.h>
using namespace std;
bool isUp( int i, int arr[], int N)
{
return (i > 0 && i < N - 1
&& arr[i] < arr[i - 1]
&& arr[i] < arr[i + 1]);
}
bool isDown( int i, int arr[], int N)
{
return (i > 0 && i < N - 1
&& arr[i] > arr[i - 1]
&& arr[i] > arr[i + 1]);
}
int solve( int arr[], int N)
{
bool mark[N] = { 0 };
int total = 0;
for ( int i = 1; i < N - 1; i++) {
if (arr[i] > arr[i + 1]
&& arr[i] > arr[i - 1]) {
mark[i] = 1;
total++;
}
else if (arr[i] < arr[i + 1]
&& arr[i] < arr[i - 1]) {
mark[i] = 1;
total++;
}
}
int ans = total;
for ( int i = 1; i < N - 1; i++) {
int temp = arr[i];
arr[i] = arr[i - 1];
ans
= min(
ans,
total - mark[i - 1] - mark[i]
- mark[i + 1]
+ isUp(i - 1, arr, N)
+ isDown(i - 1, arr, N)
+ isUp(i, arr, N)
+ isDown(i, arr, N)
+ isUp(i + 1, arr, N)
+ isDown(i + 1, arr, N));
arr[i] = arr[i + 1];
ans
= min(
ans,
total
- mark[i - 1] - mark[i]
- mark[i + 1]
+ isUp(i - 1, arr, N)
+ isDown(i - 1, arr, N)
+ isUp(i, arr, N)
+ isDown(i, arr, N)
+ isUp(i + 1, arr, N)
+ isDown(i + 1, arr, N));
arr[i] = temp;
}
return ans;
}
int main()
{
int arr[] = { 1, 4, 3, 5, 3, 8 };
int N = sizeof (arr) / sizeof ( int );
cout << solve(arr, N);
return 0;
}
|
Java
import java.util.*;
class GFG{
static int isUp( int i, int arr[], int N)
{
if (i > 0 && i < N - 1
&& arr[i] < arr[i - 1 ]
&& arr[i] < arr[i + 1 ])
{
return 1 ;
}
else
return 0 ;
}
static int isDown( int i, int arr[], int N)
{
if (i > 0 && i < N - 1
&& arr[i] > arr[i - 1 ]
&& arr[i] > arr[i + 1 ])
{
return 1 ;
}
else
return 0 ;
}
static int solve( int arr[], int N)
{
int mark[] = new int [N] ;
int total = 0 ;
for ( int i = 1 ; i < N - 1 ; i++) {
if (arr[i] > arr[i + 1 ]
&& arr[i] > arr[i - 1 ]) {
mark[i] = 1 ;
total++;
}
else if (arr[i] < arr[i + 1 ]
&& arr[i] < arr[i - 1 ]) {
mark[i] = 1 ;
total++;
}
}
int ans = total;
for ( int i = 1 ; i < N - 1 ; i++) {
int temp = arr[i];
arr[i] = arr[i - 1 ];
ans
= Math.min(
ans,
total - mark[i - 1 ] - mark[i]
- mark[i + 1 ]
+ isUp(i - 1 , arr, N)
+ isDown(i - 1 , arr, N)
+ isUp(i, arr, N)
+ isDown(i, arr, N)
+ isUp(i + 1 , arr, N)
+ isDown(i + 1 , arr, N));
arr[i] = arr[i + 1 ];
ans
= Math.min(
ans,
total
- mark[i - 1 ] - mark[i]
- mark[i + 1 ]
+ isUp(i - 1 , arr, N)
+ isDown(i - 1 , arr, N)
+ isUp(i, arr, N)
+ isDown(i, arr, N)
+ isUp(i + 1 , arr, N)
+ isDown(i + 1 , arr, N));
arr[i] = temp;
}
return ans;
}
public static void main(String[] args)
{
int arr[] = { 1 , 4 , 3 , 5 , 3 , 8 };
int N = arr.length;
System.out.print(solve(arr, N));
}
}
|
Python3
def isUp (i, arr, N):
return (i > 0 and i < N - 1
and arr[i] < arr[i - 1 ]
and arr[i] < arr[i + 1 ]);
def isDown (i, arr, N):
return (i > 0 and i < N - 1
and arr[i] > arr[i - 1 ]
and arr[i] > arr[i + 1 ]);
def solve (arr, N):
mark = [ 0 ] * N
total = 0 ;
for i in range ( 1 , N - 1 ):
if (arr[i] > arr[i + 1 ] and arr[i] > arr[i - 1 ]):
mark[i] = 1 ;
total + = 1
elif (arr[i] < arr[i + 1 ]
and arr[i] < arr[i - 1 ]):
mark[i] = 1 ;
total + = 1
ans = total;
for i in range ( 1 , N - 1 ):
temp = arr[i];
arr[i] = arr[i - 1 ];
ans = min (
ans,
total - mark[i - 1 ] - mark[i]
- mark[i + 1 ]
+ isUp(i - 1 , arr, N)
+ isDown(i - 1 , arr, N)
+ isUp(i, arr, N)
+ isDown(i, arr, N)
+ isUp(i + 1 , arr, N)
+ isDown(i + 1 , arr, N));
arr[i] = arr[i + 1 ];
ans = min (
ans,
total
- mark[i - 1 ] - mark[i]
- mark[i + 1 ]
+ isUp(i - 1 , arr, N)
+ isDown(i - 1 , arr, N)
+ isUp(i, arr, N)
+ isDown(i, arr, N)
+ isUp(i + 1 , arr, N)
+ isDown(i + 1 , arr, N));
arr[i] = temp;
return ans;
arr = [ 1 , 4 , 3 , 5 , 3 , 8 ];
N = len (arr)
print (solve(arr, N));
|
C#
using System;
class GFG {
static int isUp( int i, int []arr, int N)
{
if (i > 0 && i < N - 1
&& arr[i] < arr[i - 1]
&& arr[i] < arr[i + 1])
{
return 1;
}
else
return 0;
}
static int isDown( int i, int []arr, int N)
{
if (i > 0 && i < N - 1
&& arr[i] > arr[i - 1]
&& arr[i] > arr[i + 1])
{
return 1;
}
else
return 0;
}
static int solve( int []arr, int N)
{
int []mark = new int [N] ;
int total = 0;
for ( int i = 1; i < N - 1; i++) {
if (arr[i] > arr[i + 1]
&& arr[i] > arr[i - 1]) {
mark[i] = 1;
total++;
}
else if (arr[i] < arr[i + 1]
&& arr[i] < arr[i - 1]) {
mark[i] = 1;
total++;
}
}
int ans = total;
for ( int i = 1; i < N - 1; i++) {
int temp = arr[i];
arr[i] = arr[i - 1];
ans
= Math.Min(
ans,
total - mark[i - 1] - mark[i]
- mark[i + 1]
+ isUp(i - 1, arr, N)
+ isDown(i - 1, arr, N)
+ isUp(i, arr, N)
+ isDown(i, arr, N)
+ isUp(i + 1, arr, N)
+ isDown(i + 1, arr, N));
arr[i] = arr[i + 1];
ans
= Math.Min(
ans,
total
- mark[i - 1] - mark[i]
- mark[i + 1]
+ isUp(i - 1, arr, N)
+ isDown(i - 1, arr, N)
+ isUp(i, arr, N)
+ isDown(i, arr, N)
+ isUp(i + 1, arr, N)
+ isDown(i + 1, arr, N));
arr[i] = temp;
}
return ans;
}
public static void Main()
{
int []arr = { 1, 4, 3, 5, 3, 8 };
int N = arr.Length;
Console.Write(solve(arr, N));
}
}
|
Javascript
<script>
const isUp = (i, arr, N) => {
return (i > 0 && i < N - 1
&& arr[i] < arr[i - 1]
&& arr[i] < arr[i + 1]);
}
const isDown = (i, arr, N) => {
return (i > 0 && i < N - 1
&& arr[i] > arr[i - 1]
&& arr[i] > arr[i + 1]);
}
const solve = (arr, N) => {
let mark = new Array(N).fill(0);
let total = 0;
for (let i = 1; i < N - 1; i++) {
if (arr[i] > arr[i + 1]
&& arr[i] > arr[i - 1]) {
mark[i] = 1;
total++;
}
else if (arr[i] < arr[i + 1]
&& arr[i] < arr[i - 1]) {
mark[i] = 1;
total++;
}
}
let ans = total;
for (let i = 1; i < N - 1; i++) {
let temp = arr[i];
arr[i] = arr[i - 1];
ans = Math.min(
ans,
total - mark[i - 1] - mark[i]
- mark[i + 1]
+ isUp(i - 1, arr, N)
+ isDown(i - 1, arr, N)
+ isUp(i, arr, N)
+ isDown(i, arr, N)
+ isUp(i + 1, arr, N)
+ isDown(i + 1, arr, N));
arr[i] = arr[i + 1];
ans = Math.min(
ans,
total
- mark[i - 1] - mark[i]
- mark[i + 1]
+ isUp(i - 1, arr, N)
+ isDown(i - 1, arr, N)
+ isUp(i, arr, N)
+ isDown(i, arr, N)
+ isUp(i + 1, arr, N)
+ isDown(i + 1, arr, N));
arr[i] = temp;
}
return ans;
}
let arr = [1, 4, 3, 5, 3, 8];
let N = arr.length;
document.write(solve(arr, N));
</script>
|
Time Complexity: O(N)
Auxiliary Space: O(N)
Like Article
Suggest improvement
Share your thoughts in the comments
Please Login to comment...