Given an array of size N containing all elements as 0 initially, and a Q queries containing range in the form of [L, R]. The task is to modify the array by adding 1 to each element in the range [L, R] for Q queries and then print the size of minimum length subarray containing all unique elements.
Note: 1-based indexing is used in the range [L, R].
Examples:
Input: N = 6, Q[4][] = {{1, 3}, {4, 6}, {3, 4}, {3, 3}}
Output: 3
Explanation:
Initial array: arr[] = { 0, 0, 0, 0, 0, 0 }
Query 1: updated arr[] = { 1, 1, 1, 0, 0, 0 }.
Query 2: updated arr[] = { 1, 1, 1, 1, 1, 1 }.
Query 3: updated arr[] = { 1, 1, 2, 2, 1, 1 }.
Query 4: updated arr[] = { 1, 1, 3, 2, 1, 1 }.
The subarray { 1, 3, 2 } is minimum subarray which contains all unique elements. Thus, the answer is 3.
Input: N = 8, Q[6][] = {{1, 4}, {3, 4}, {4, 5}, {5, 5}, {7, 8}, {8, 8}}
Output: 4
Explanation:
After processing all queries, the array becomes = { 1, 1, 2, 3, 2, 0, 1, 2 }.
The subarray { 3, 2, 0, 1 } is minimum subarray which contains all unique elements. Thus, the answer is 4.
Approach: The idea is to use the concept of Prefix sum array and Two pointers approach to this problem.
- Final Array after the queries can be computed by incrementing the value at the array by 1 at the index L and decrementing the value by 1 at the index R + 1.
Processing of a Query: arr[L] += 1 arr[R + 1] -= 1
- Finally, compute the Prefix sum of the array to compute the final array after the queries. Then use Two pointers approach to get the minimum length subarray containing all unique elements.
Below is the implementation of the above approach:
// C++ implementation to find the // minimum size subarray containing // all unique elements after processing // the array for K queries of ranges #include <bits/stdc++.h> using namespace std;
// Function to find minimum size subarray // of all array elements int subarrayLength( int A[], int R[][2],
int N, int M)
{ // Updating the array after
// processing each query
for ( int i = 0; i < M; ++i) {
int l = R[i][0], r = R[i][1] + 1;
// Making it to 0-indexing
l--;
r--;
// Prefix sum array concept is used
// to obtain the count array
A[l]++;
if (r < N)
A[r]--;
}
// Iterating over the array
// to get the final array
for ( int i = 1; i < N; ++i) {
A[i] += A[i - 1];
}
// Variable to get count
// of all unique elements
int count = 0;
// Hash to maintain previously
// occurred elements
unordered_set< int > s;
// Loop to find the all
// unique elements
for ( int i = 0; i < N; ++i) {
if (s.find(A[i]) == s.end())
count++;
s.insert(A[i]);
}
// array to maintain counter
// of encountered elements
vector< int > repeat(count + 1, 0);
// variable to store answer
int ans = N;
// Using two pointers approach
int counter = 0, left = 0, right = 0;
while (right < N) {
int cur_element = A[right];
repeat[cur_element] += 1;
// Increment counter
// if occurred once
if (repeat[cur_element] == 1)
++counter;
// when all unique
// elements are found
while (counter == count) {
// update answer with
// minimum size
ans = min(ans, right - left + 1);
// decrement count of
// elements from left
cur_element = A[left];
repeat[cur_element] -= 1;
++left;
// decrement counter
if (repeat[cur_element] == 0)
--counter;
}
++right;
}
return ans;
} // Driver code int main()
{ int N = 8, queries = 6;
int Q[][2]
= {
{ 1, 4 }, { 3, 4 }, { 4, 5 },
{ 5, 5 }, { 7, 8 }, { 8, 8 }
};
int A[N] = { 0 };
cout << subarrayLength(A, Q, N, queries);
return 0;
} |
// Java implementation to find the // minimum size subarray containing // all unique elements after processing // the array for K queries of ranges import java.util.*;
class GFG{
// Function to find minimum size subarray // of all array elements static int subarrayLength( int A[], int R[][],
int N, int M)
{ // Updating the array after
// processing each query
for ( int i = 0 ; i < M; ++i)
{
int l = R[i][ 0 ], r = R[i][ 1 ] + 1 ;
// Making it to 0-indexing
l--;
r--;
// Prefix sum array concept is used
// to obtain the count array
A[l]++;
if (r < N)
A[r]--;
}
// Iterating over the array
// to get the final array
for ( int i = 1 ; i < N; ++i)
{
A[i] += A[i - 1 ];
}
// Variable to get count
// of all unique elements
int count = 0 ;
// Hash to maintain previously
// occurred elements
HashSet<Integer> s = new HashSet<Integer>();
// Loop to find the all
// unique elements
for ( int i = 0 ; i < N; ++i)
{
if (!s.contains(A[i]))
count++;
s.add(A[i]);
}
// array to maintain counter
// of encountered elements
int []repeat = new int [count + 1 ];
// variable to store answer
int ans = N;
// Using two pointers approach
int counter = 0 , left = 0 , right = 0 ;
while (right < N)
{
int cur_element = A[right];
repeat[cur_element] += 1 ;
// Increment counter
// if occurred once
if (repeat[cur_element] == 1 )
++counter;
// when all unique
// elements are found
while (counter == count)
{
// update answer with
// minimum size
ans = Math.min(ans,
right - left + 1 );
// decrement count of
// elements from left
cur_element = A[left];
repeat[cur_element] -= 1 ;
++left;
// decrement counter
if (repeat[cur_element] == 0 )
--counter;
}
++right;
}
return ans;
} // Driver code public static void main(String[] args)
{ int N = 8 , queries = 6 ;
int Q[][] = {{ 1 , 4 }, { 3 , 4 }, { 4 , 5 },
{ 5 , 5 }, { 7 , 8 }, { 8 , 8 }};
int A[] = new int [N];
System.out.print(subarrayLength(A, Q,
N, queries));
} } // This code is contributed by Rajput-Ji |
# Python3 implementation to find the # minimum size subarray containing # all unique elements after processing # the array for K queries of ranges # Function to find minimum size subarray # of all array elements def subarrayLength(A, R, N, M):
# Updating the array after
# processing each query
for i in range (M):
l = R[i][ 0 ]
r = R[i][ 1 ] + 1
# Making it to 0-indexing
l - = 1
r - = 1
# Prefix sum array concept is used
# to obtain the count array
A[l] + = 1
if (r < N):
A[r] - = 1
# Iterating over the array
# to get the final array
for i in range ( 1 , N):
A[i] + = A[i - 1 ]
# Variable to get count
# of all unique elements
count = 0
# Hash to maintain previously
# occurred elements
s = []
# Loop to find the all
# unique elements
for i in range (N):
if (A[i] not in s):
count + = 1
s.append(A[i])
# Array to maintain counter
# of encountered elements
repeat = [ 0 ] * (count + 1 )
# Variable to store answer
ans = N
# Using two pointers approach
counter, left, right = 0 , 0 , 0
while (right < N):
cur_element = A[right]
repeat[cur_element] + = 1
# Increment counter
# if occurred once
if (repeat[cur_element] = = 1 ):
counter + = 1
# When all unique
# elements are found
while (counter = = count):
# update answer with
# minimum size
ans = min (ans, right - left + 1 )
# Decrement count of
# elements from left
cur_element = A[left]
repeat[cur_element] - = 1
left + = 1
# Decrement counter
if (repeat[cur_element] = = 0 ):
counter - = 1
right + = 1
return ans
# Driver code if __name__ = = "__main__" :
N , queries = 8 , 6
Q = [ [ 1 , 4 ], [ 3 , 4 ], [ 4 , 5 ],
[ 5 , 5 ], [ 7 , 8 ], [ 8 , 8 ] ]
A = [ 0 ] * N
print (subarrayLength(A, Q, N, queries))
# This code is contributed by chitranayal |
// C# implementation to find the // minimum size subarray containing // all unique elements after processing // the array for K queries of ranges using System;
using System.Collections.Generic;
class GFG{
// Function to find minimum size subarray // of all array elements static int subarrayLength( int []A, int [,]R,
int N, int M)
{ // Updating the array after
// processing each query
for ( int i = 0; i < M; ++i)
{
int l = R[i, 0], r = R[i, 1] + 1;
// Making it to 0-indexing
l--;
r--;
// Prefix sum array concept is used
// to obtain the count array
A[l]++;
if (r < N)
A[r]--;
}
// Iterating over the array
// to get the readonly array
for ( int i = 1; i < N; ++i)
{
A[i] += A[i - 1];
}
// Variable to get count
// of all unique elements
int count = 0;
// Hash to maintain previously
// occurred elements
HashSet< int > s = new HashSet< int >();
// Loop to find the all
// unique elements
for ( int i = 0; i < N; ++i)
{
if (!s.Contains(A[i]))
count++;
s.Add(A[i]);
}
// Array to maintain counter
// of encountered elements
int []repeat = new int [count + 1];
// Variable to store answer
int ans = N;
// Using two pointers approach
int counter = 0, left = 0, right = 0;
while (right < N)
{
int cur_element = A[right];
repeat[cur_element] += 1;
// Increment counter
// if occurred once
if (repeat[cur_element] == 1)
++counter;
// When all unique
// elements are found
while (counter == count)
{
// Update answer with
// minimum size
ans = Math.Min(ans,
right - left + 1);
// Decrement count of
// elements from left
cur_element = A[left];
repeat[cur_element] -= 1;
++left;
// Decrement counter
if (repeat[cur_element] == 0)
--counter;
}
++right;
}
return ans;
} // Driver code public static void Main(String[] args)
{ int N = 8, queries = 6;
int [,]Q = { { 1, 4 }, { 3, 4 }, { 4, 5 },
{ 5, 5 }, { 7, 8 }, { 8, 8 } };
int []A = new int [N];
Console.Write(subarrayLength(A, Q,
N, queries));
} } // This code is contributed by Amit Katiyar |
<script> // Javascript implementation to find the // minimum size subarray containing // all unique elements after processing // the array for K queries of ranges // Function to find minimum size subarray // of all array elements function subarrayLength(A, R, N, M)
{ // Updating the array after
// processing each query
for (let i = 0; i < M; ++i)
{
let l = R[i][0], r = R[i][1] + 1;
// Making it to 0-indexing
l--;
r--;
// Prefix sum array concept is used
// to obtain the count array
A[l]++;
if (r < N)
A[r]--;
}
// Iterating over the array
// to get the final array
for (let i = 1; i < N; ++i)
{
A[i] += A[i - 1];
}
// Variable to get count
// of all unique elements
let count = 0;
// Hash to maintain previously
// occurred elements
let s = new Set();
// Loop to find the all
// unique elements
for (let i = 0; i < N; ++i)
{
if (!s.has(A[i]))
count++;
s.add(A[i]);
}
// array to maintain counter
// of encountered elements
let repeat = Array.from({length: count + 1}, (_, i) => 0);
// variable to store answer
let ans = N;
// Using two pointers approach
let counter = 0, left = 0, right = 0;
while (right < N)
{
let cur_element = A[right];
repeat[cur_element] += 1;
// Increment counter
// if occurred once
if (repeat[cur_element] == 1)
++counter;
// when all unique
// elements are found
while (counter == count)
{
// update answer with
// minimum size
ans = Math.min(ans,
right - left + 1);
// decrement count of
// elements from left
cur_element = A[left];
repeat[cur_element] -= 1;
++left;
// decrement counter
if (repeat[cur_element] == 0)
--counter;
}
++right;
}
return ans;
} // Driver code let N = 8, queries = 6;
let Q = [[ 1, 4 ], [ 3, 4 ], [ 4, 5 ],
[ 5, 5 ], [ 7, 8 ], [ 8, 8 ]];
let A = Array.from({length: N}, (_, i) => 0);
document.write(subarrayLength(A, Q,
N, queries));
</script> |
4
Time Complexity: O(N)