Longest subsequence such that difference of max and min is at-most K
Last Updated :
06 Mar, 2023
Given an array arr[] of length N, the task is to find the length of longest subsequence such that the difference of its maximum element and minimum element is not more than an integer K.
A sequence a is a subsequence of a sequence b if ????a can be obtained from b by deletion of several (possibly, zero) elements. For example, [3,1][3,1] is a subsequence of [3,2,1][3,2,1] and [4,3,1][4,3,1], but not a subsequence of [1,3,3,7][1,3,3,7] and [3,10,4][3,10,4].
Examples:
Input: K = 3, arr[]= {1, 4, 5, 6, 9}
Output: 3
Explanation:
Largest Subarray is {4, 5, 6}
Input: K = 4, arr[]= {1, 2, 3, 4, 5}
Output: 5
Explanation:
Largest Subarray is {1, 2, 3, 4, 5}
Naive approach:
Time Complexity: O(2N)
Efficient approach: The idea is to first sort the array, and then use binary search to optimize the approach.
- Sort the given array
- For every distinct element A[i] in the array find the first element A[j] such that (A[j]-A[i]) > K.
- For its implementation we use Binary search or lower_bound and update ans each time as maximum of previous ans and difference of indixes.
Below is the implementation of the above approach:
C++
// C++ program to find longest
// subarray such that difference
// of max and min is at-most K
#include <bits/stdc++.h>
using namespace std;
// Function to calculate longest
// subarray with above condition
int findLargestSubarray(
vector<int>& arr,
int N, int K)
{
// Sort the array
sort(arr.begin(), arr.end());
int value1 = arr[0], value2 = 0;
int index1, index2, i, MAX;
index1 = index2 = 0;
i = 0, MAX = 0;
// Loop which will terminate
// when no further elements
// can be included in the subarray
while (index2 != N) {
// first value such that
// arr[index2] - arr[index1] > K
value2 = value1 + (K + 1);
// calculate its index using lower_bound
index2 = lower_bound(arr.begin(),
arr.end(), value2)
- arr.begin();
// index2- index1 will give
// the accurate length
// of subarray then compare
// for MAX length and store
// in MAX variable
MAX = max(MAX, (index2 - index1));
// change the index1
// to next greater element
// than previous one
// and recalculate the value1
index1
= lower_bound(
arr.begin(),
arr.end(), arr[index1] + 1)
- arr.begin();
value1 = arr[index1];
}
// finally return answer MAX
return MAX;
}
// Driver Code
int main()
{
int N, K;
N = 18;
K = 5;
vector<int> arr{ 1, 1, 1, 2, 2,
2, 2, 2, 3,
3, 3, 6, 6, 7,
7, 7, 7, 7 };
cout << findLargestSubarray(arr, N, K);
return 0;
}
Java
import java.util.*;
class GFG {
// Function to calculate longest subarray with above condition
static int findLargestSubarray(
ArrayList<Integer> arr, int N, int K)
{
// Sort the array
Collections.sort(arr);
int value1 = arr.get(0), value2 = 0;
int index1, index2, i, MAX;
index1 = index2 = 0;
i = 0;
MAX = 0;
// Loop which will terminate when no further elements can be included in the subarray
while (index2 != N) {
// first value such that arr[index2] - arr[index1] > K
value2 = value1 + (K + 1);
// calculate its index using binary search
index2 = Collections.binarySearch(arr, value2);
// If the value is not found, then the method returns (-(insertion point) - 1)
if (index2 < 0) {
index2 = -(index2 + 1);
}
// index2- index1 will give the accurate length of subarray then compare
// for MAX length and store in MAX variable
MAX = Math.max(MAX, (index2 - index1));
// change the index1 to next greater element than previous one and recalculate the value1
index1 = Collections.binarySearch(arr, arr.get(index1) + 1);
if (index1 < 0) {
index1 = -(index1 + 1);
}
value1 = arr.get(index1);
}
// finally return answer MAX
return MAX;
}
// Driver Code
public static void main(String[] args)
{
int N, K;
N = 18;
K = 5;
ArrayList<Integer> arr = new ArrayList<Integer>(Arrays.asList(1, 1, 1, 2, 2,
2, 2, 2, 3,
3, 3, 6, 6, 7,
7, 7, 7, 7));
System.out.println(findLargestSubarray(arr, N, K));
}
}
Python3
# Python program to find longest
# subarray such that difference
# of max and min is at-most K
from bisect import bisect_left
# Function to calculate longest
# subarray with above condition
def findLargestSubarray(arr, N, K):
# Sort the array
arr.sort()
value1 = arr[0]
value2 = 0
index1, index2 = 0, 0
i, MAX = 0, 0
# Loop which will terminate
# when no further elements
# can be included in the subarray
while index2 != N:
# first value such that
# arr[index2] - arr[index1] > K
value2 = value1 + (K + 1)
# calculate its index using bisect_left
index2 = bisect_left(arr, value2)
# index2- index1 will give
# the accurate length
# of subarray then compare
# for MAX length and store
# in MAX variable
MAX = max(MAX, (index2 - index1))
# change the index1
# to next greater element
# than previous one
# and recalculate the value1
index1 = bisect_left(arr, arr[index1] + 1)
value1 = arr[index1]
# finally return answer MAX
return MAX
# Driver Code
if __name__ == '__main__':
N = 18
K = 5
arr = [1, 1, 1, 2, 2, 2, 2, 2, 3, 3, 3, 6, 6, 7, 7, 7, 7, 7]
print(findLargestSubarray(arr, N, K))
C#
using System;
using System.Collections.Generic;
using System.Linq;
class GFG
{
static int findLargestSubarray(List<int> arr, int N, int K)
{
// Sort the array
arr.Sort();
int value1 = arr[0], value2 = 0;
int index1, index2, i, MAX;
index1 = index2 = 0;
i = 0;
MAX = 0;
// Loop which will terminate when no further elements can be included in the subarray
while (index2 != N)
{
// first value such that arr[index2] - arr[index1] > K
value2 = value1 + (K + 1);
// calculate its index using binary search
index2 = arr.BinarySearch(value2);
// If the value is not found, then the method returns (-(insertion point) - 1)
if (index2 < 0)
{
index2 = -(index2 + 1);
}
// index2- index1 will give the accurate length of subarray then compare
// for MAX length and store in MAX variable
MAX = Math.Max(MAX, (index2 - index1));
// change the index1 to next greater element than previous one and recalculate the value1
index1 = arr.BinarySearch(arr[index1] + 1);
if (index1 < 0)
{
index1 = -(index1 + 1);
}
value1 = arr[index1];
}
// finally return answer MAX
return MAX;
}
static void Main(string[] args)
{
int N, K;
N = 18;
K = 5;
List<int> arr = new List<int>(new int[] { 1, 1, 1, 2, 2, 2, 2, 2, 3, 3, 3, 6, 6, 7, 7, 7, 7, 7 });
Console.WriteLine(findLargestSubarray(arr, N, K));
}
}
//contributed by adityasharmadev01
JavaScript
// Javascript program for the above approach
function bisect_left(arr, x) {
let lo = 0, hi = arr.length;
while (lo < hi) {
let mid = (lo + hi) >> 1;
if (arr[mid] < x) {
lo = mid + 1;
} else {
hi = mid;
}
}
return lo;
}
function findLargestSubarray(arr, N, K) {
// Sort the array
arr.sort((a, b) => a - b);
let value1 = arr[0];
let value2 = 0;
let index1 = 0, index2 = 0;
let MAX = 0;
// Loop which will terminate
// when no further elements
// can be included in the subarray
while (index2 != N) {
// first value such that
// arr[index2] - arr[index1] > K
value2 = value1 + (K + 1);
// calculate its index using bisect_left
index2 = bisect_left(arr, value2);
// index2- index1 will give
// the accurate length
// of subarray then compare
// for MAX length and store
// in MAX variable
MAX = Math.max(MAX, (index2 - index1));
// change the index1
// to next greater element
// than previous one
// and recalculate the value1
index1 = bisect_left(arr, arr[index1] + 1);
value1 = arr[index1];
}
// finally return answer MAX
return MAX;
}
// Driver Code
let N = 18;
let K = 5;
let arr = [1, 1, 1, 2, 2, 2, 2, 2, 3, 3, 3, 6, 6, 7, 7, 7, 7, 7];
console.log(findLargestSubarray(arr, N, K));
// contributed by adityasharmadev01
Time Complexity: O(N*log(N))
Auxiliary Space: O(1)
Similar Reads
Longest Subsequence with difference between max and min at most K Given an array arr[] of size N and a non-negative integer K, the task is to find the length of the longest subsequence such that the difference between the maximum and the minimum of the subsequence is at most K. Examples: Input: arr[] = {1, 3, 5, 4, 2}, N = 5, K = 3Output: 4Explanation: If we consi
5 min read
Longest subarray such that the difference of max and min is at-most one Given an array of n numbers where the difference between each number and the previous one doesn't exceed one. Find the longest contiguous subarray such that the difference between the maximum and minimum number in the range doesn't exceed one. Examples: Input : {3, 3, 4, 4, 5, 6} Output : 4 The long
7 min read
Longest subsequence such that difference between adjacents is one | Set 2 Given an array of size n. The task is to find the longest subsequence such that difference between adjacents is one. Time Complexity of O(n) is required.Examples: Input : arr[] = {10, 9, 4, 5, 4, 8, 6} Output : 3 As longest subsequences with difference 1 are, "10, 9, 8", "4, 5, 4" and "4, 5, 6". Inp
8 min read
Longest subsequence such that difference between adjacents is one Given an array arr[] of size n, the task is to find the longest subsequence such that the absolute difference between adjacent elements is 1.Examples: Input: arr[] = [10, 9, 4, 5, 4, 8, 6]Output: 3Explanation: The three possible subsequences of length 3 are [10, 9, 8], [4, 5, 4], and [4, 5, 6], wher
15+ min read
Print longest Subsequence such that difference between adjacent elements is K Given an array arr[] of size N, and integer K. The task is to find the longest subsequence with the difference between adjacent elements as K Examples: Input: arr[] = { 5, 5, 5, 10, 8, 6, 12, 13 }, K = 1Output: {5, 6} Input: arr[] = {4, 6, 7, 8, 9, 8, 12, 14, 17, 15}, K = 2Output: {4, 6, 8} Approach
9 min read