Count unique subsequences of length K
Last Updated :
20 Dec, 2022
Given an array of N numbers and an integer K. The task is to print the number of unique subsequences possible of length K.
Examples:
Input : a[] = {1, 2, 3, 4}, k = 3
Output : 4.
Unique Subsequences are:
{1, 2, 3}, {1, 2, 4}, {1, 3, 4}, {2, 3, 4}
Input: a[] = {1, 1, 1, 2, 2, 2 }, k = 3
Output : 4
Unique Subsequences are
{1, 1, 1}, {1, 1, 2}, {1, 2, 2}, {2, 2, 2}
Approach:
There is a well-known formula for how many subsequences of fixed length K can be chosen from N unique objects. But the problem here has several differences. One among them is the order in subsequences is important and must be preserved as in the original sequence. For such a problem there can be no ready combinatorics formula because the results depend on the order of the original array.
The main idea is to deal recurrently by the length of the subsequence. On each recurrent step, move from the end to the beginning and count the unique combinations using the count of shorter unique combinations from the previous step. More strictly on every step j, we keep an array of length N and every element in the place p means how many unique subsequences with length j we found to the right of the element in place i, including i itself.
Below is the implementation of the above approach.
C++
#include <bits/stdc++.h>
using namespace std;
// Function which returns the number of
// unique subsequences of length K
int solution(vector<int>& A, int k)
{
// size of the vector
// which is constant
const int N = A.size();
// base cases
if (N < k || N < 1 || k < 1)
return 0;
if (N == k)
return 1;
// Prepare vectors for recursion
vector<int> v1(N, 0);
vector<int> v2(N, 0);
vector<int> v3(N, 0);
// initialize separately for k = 1
// initialize the last element
v2[N - 1] = 1;
v3[A[N - 1] - 1] = 1;
// initiate all other elements of k = 1
for (int i = N - 2; i >= 0; i--) {
// initialize the front element
// to vector v2
v2[i] = v2[i + 1];
// if element v[a[i]-1] is 0
// then increment it in vector v2
if (v3[A[i] - 1] == 0) {
v2[i]++;
v3[A[i] - 1] = 1;
}
}
// iterate for all possible values of K
for (int j = 1; j < k; j++) {
// fill the vectors with 0
fill(v3.begin(), v3.end(), 0);
// fill(v1.begin(), v1.end(), 0)
// the last must be 0 as from last no unique
// subarray can be formed
v1[N - 1] = 0;
// Iterate for all index from which unique
// subsequences can be formed
for (int i = N - 2; i >= 0; i--) {
// add the number of subsequence formed
// from the next index
v1[i] = v1[i + 1];
// start with combinations on the
// next index
v1[i] = v1[i] + v2[i + 1];
// Remove the elements which have
// already been counted
v1[i] = v1[i] - v3[A[i] - 1];
// Update the number used
v3[A[i] - 1] = v2[i + 1];
}
// prepare the next iteration
// by filling v2 in v1
v2 = v1;
}
// last answer is stored in v2
return v2[0];
}
// Function to push the vector into an array
// and print all the unique subarrays
void solve(int a[], int n, int k)
{
vector<int> v;
// fill the vector with a[]
v.assign(a, a + n);
// Function call to print the count
// of unique subsequences of size K
cout << solution(v, k);
}
// Driver Code
int main()
{
int a[] = { 1, 2, 3, 4 };
int n = sizeof(a) / sizeof(a[0]);
int k = 3;
solve(a, n, k);
return 0;
}
Java
import java.util.*;
class GFG{
// Function which returns the numbe of
// unique subsequences of length K
static int solution(int[] A, int N, int k)
{
// Bases cases
if (N < k || N < 1 || k < 1)
return 0;
if (N == k)
return 1;
// Prepare arrays for recursion
int[] v1 = new int[N];
int[] v2 = new int[N];
int[] v3 = new int[N];
// Initiate separately for k = 1
// initiate the last element
v2[N - 1] = 1;
v3[A[N - 1] - 1] = 1;
// Initiate all other elements of k = 1
for(int i = N - 2; i >= 0; i--)
{
// Initialize the front element
// to vector v2
v2[i] = v2[i + 1];
// If element v[a[i]-1] is 0
// then increment it in vector v2
if (v3[A[i] - 1] == 0)
{
v2[i]++;
v3[A[i] - 1] = 1;
}
}
// Iterate for all possible values of K
for(int j = 1; j < k; j++)
{
// Fill the vectors with 0
Arrays.fill(v3, 0);
// Fill(v1.begin(), v1.end(), 0)
// the last must be 0 as from last
// no unique subarray can be formed
v1[N - 1] = 0;
// Iterate for all index from which
// unique subsequences can be formed
for(int i = N - 2; i >= 0; i--)
{
// Add the number of subsequence
// formed from the next index
v1[i] = v1[i + 1];
// Start with combinations on the
// next index
v1[i] = v1[i] + v2[i + 1];
// Remove the elements which have
// already been counted
v1[i] = v1[i] - v3[A[i] - 1];
// Update the number used
v3[A[i] - 1] = v2[i + 1];
}
}
// Last answer is stored in v2
return v2[0];
}
// Driver Code
public static void main(String[] args)
{
int a[] = { 1, 2, 3, 4 };
int n = a.length;
int k = 3;
System.out.print(solution(a, n, k));
}
}
// This code is contributed by amal kumar choubey
Python3
# Function which returns the numbe of
# unique subsequences of length K
def solution( A, k):
# seiz of the vector
# which does is constant
N = len(A)
# bases cases
if (N < k or N < 1 or k < 1):
return 0
if (N == k):
return 1
# Prepare arrays for recursion
v1 = [0]*(N)
v2 = [0]*N
v3 = [0]*N
# initiate separately for k = 1
# initiate the last element
v2[N - 1] = 1
v3[A[N - 1] - 1] = 1
# initiate all other elements of k = 1
for i in range(N - 2,-1,-1):
# initialize the front element
# to vector v2
v2[i] = v2[i + 1]
# if element v[a[i]-1] is 0
# then increment it in vector v2
if (v3[A[i] - 1] == 0):
v2[i] += 1
v3[A[i] - 1] = 1
# iterate for all possible values of K
for j in range( 1, k) :
# fill the vectors with 0
v3 = [0]*N
# fill(v1.begin(), v1.end(), 0)
# the last must be 0 as from last no unique
# subarray can be formed
v1[N - 1] = 0
# Iterate for all index from which unique
# subsequences can be formed
for i in range( N - 2, -1, -1) :
# add the number of subsequence formed
# from the next index
v1[i] = v1[i + 1]
# start with combinations on the
# next index
v1[i] = v1[i] + v2[i + 1]
# Remove the elements which have
# already been counted
v1[i] = v1[i] - v3[A[i] - 1]
# Update the number used
v3[A[i] - 1] = v2[i + 1]
# prepare the next iteration
# by filling v2 in v1
for i in range(len(v1)):
v2[i] = v1[i]
# last answer is stored in v2
return v2[0]
# Function to push the vector into an array
# and print all the unique subarrays
def solve(a, n, k):
# fill the vector with a[]
v = a
# Function call to print the count
# of unique subsequences of size K
print( solution(v, k))
# Driver Code
if __name__ == "__main__":
a = [ 1, 2, 3, 4 ]
n = len(a)
k = 3
solve(a, n, k)
# This code is contributed by chitranayal
C#
using System;
class GFG{
// Function which returns the numbe of
// unique subsequences of length K
static int solution(int[] A, int N, int k)
{
// Bases cases
if (N < k || N < 1 || k < 1)
return 0;
if (N == k)
return 1;
// Prepare arrays for recursion
int[] v1 = new int[N];
int[] v2 = new int[N];
int[] v3 = new int[N];
// Initiate separately for k = 1
// initiate the last element
v2[N - 1] = 1;
v3[A[N - 1] - 1] = 1;
// Initiate all other elements of k = 1
for(int i = N - 2; i >= 0; i--)
{
// Initialize the front element
// to vector v2
v2[i] = v2[i + 1];
// If element v[a[i]-1] is 0
// then increment it in vector v2
if (v3[A[i] - 1] == 0)
{
v2[i]++;
v3[A[i] - 1] = 1;
}
}
// Iterate for all possible values of K
for(int j = 1; j < k; j++)
{
// Fill the vectors with 0
for(int i = 0; i < v3.GetLength(0); i++)
v3[i] = 0;
// Fill(v1.begin(), v1.end(), 0)
// the last must be 0 as from last
// no unique subarray can be formed
v1[N - 1] = 0;
// Iterate for all index from which
// unique subsequences can be formed
for(int i = N - 2; i >= 0; i--)
{
// Add the number of subsequence
// formed from the next index
v1[i] = v1[i + 1];
// Start with combinations on the
// next index
v1[i] = v1[i] + v2[i + 1];
// Remove the elements which have
// already been counted
v1[i] = v1[i] - v3[A[i] - 1];
// Update the number used
v3[A[i] - 1] = v2[i + 1];
}
}
// Last answer is stored in v2
return v2[0];
}
// Driver Code
public static void Main(String[] args)
{
int []a = { 1, 2, 3, 4 };
int n = a.Length;
int k = 3;
Console.Write(solution(a, n, k));
}
}
// This code is contributed by Rohit_ranjan
JavaScript
<script>
// Function which returns the numbe of
// unique subsequences of length K
function solution(A, N, K)
{
// Bases cases
if (N < k || N < 1 || k < 1)
return 0;
if (N == k)
return 1;
// Prepare arrays for recursion
let v1 = new Array(N);
let v2 = new Array(N);
let v3 = new Array(N);
for(let i = 0; i < N; i++)
{
v1[i] = 0;
v2[i] = 0;
v3[i] = 0;
}
// Initiate separately for k = 1
// initiate the last element
v2[N - 1] = 1;
v3[A[N - 1] - 1] = 1;
// Initiate all other elements of k = 1
for(let i = N - 2; i >= 0; i--)
{
// Initialize the front element
// to vector v2
v2[i] = v2[i + 1];
// If element v[a[i]-1] is 0
// then increment it in vector v2
if (v3[A[i] - 1] == 0)
{
v2[i]++;
v3[A[i] - 1] = 1;
}
}
// Iterate for all possible values of K
for(let j = 1; j < k; j++)
{
// Fill the vectors with 0
for(let i = 0; i < v3.length; i++)
{
v3[i] = 0;
}
// Fill(v1.begin(), v1.end(), 0)
// the last must be 0 as from last
// no unique subarray can be formed
v1[N - 1] = 0;
// Iterate for all index from which
// unique subsequences can be formed
for(let i = N - 2; i >= 0; i--)
{
// Add the number of subsequence
// formed from the next index
v1[i] = v1[i + 1];
// Start with combinations on the
// next index
v1[i] = v1[i] + v2[i + 1];
// Remove the elements which have
// already been counted
v1[i] = v1[i] - v3[A[i] - 1];
// Update the number used
v3[A[i] - 1] = v2[i + 1];
}
}
// Last answer is stored in v2
return v2[0];
}
// Driver Code
let a = [ 1, 2, 3, 4 ];
let n = a.length;
let k = 3;
document.write(solution(a, n, k));
// This code is contributed by avanitrachhadiya2155
</script>
Complexity Analysis:
- Time Complexity: O(N * K)
- Auxiliary Space: O(N)
Similar Reads
Number of subsequences of maximum length K containing no repeated elements
Given an array arr[] of N elements and a positive integer K such that K ⤠N. The task is to find the number of subsequences of maximum length K i.e. subsequences of length 0, 1, 2, ..., K - 1, K that have all distinct elements. Examples: Input: arr[] = {2, 2, 3, 3, 5}, K = 2 Output: 14 All the valid
15 min read
Count of sub-strings of length n possible from the given string
Given a string str and an integer N, the task is to find the number of possible sub-strings of length N.Examples: Input: str = "geeksforgeeks", n = 5 Output: 9 All possible sub-strings of length 5 are "geeks", "eeksf", "eksfo", "ksfor", "sforg", "forge", "orgee", "rgeek" and "geeks".Input: str = "jg
6 min read
Count of sub-strings that are divisible by K
Given an integer K and a numeric string str (all the characters are from the range ['0', '9']). The task is to count the number of sub-strings of str that are divisible by K. Examples: Input: str = "33445", K = 11 Output: 3 Sub-strings that are divisible by 11 are "33", "44" and "3344" Input: str =
9 min read
Product of all Subsequences of size K except the minimum and maximum Elements
Given an array A[] containing N elements and an integer K. The task is to calculate the product of all elements of subsequences of size K except the minimum and the maximum elements for each subsequence. Note: Since the answer can be very large so print the final answer as mod of 109 + 7. Examples:
12 min read
Count distinct substrings that contain some characters at most k times
Given a integer k and a string str, the task is to count the number of distinct sub-strings such that each sub-string does not contain some specific characters more than k times. The specific characters are given as another string. Examples: Input: str = "ababab", anotherStr = "bcd", k = 1 Output: 5
7 min read
Count of subarrays of size K which is a permutation of numbers from 1 to K
Given an array arr of distinct integers, the task is to find the count of sub-arrays of size i having all elements from 1 to i, in other words, the sub-array is any permutation of elements from 1 to i, with 1 < = i <= N. Examples: Input: arr[] = {2, 3, 1, 5, 4} Output: 3 Explanation: we have {
6 min read
Largest substring where all characters appear at least K times | Set 2
Given a string str and an integer K, the task is to find the length of the longest sub-string S such that every character in S appears at least K times.Examples:Input: str = "aabbba", K = 3Output: 6 Explanation: In substring aabbba, each character repeats at least k times and its length is 6.Input:
7 min read
Count of contiguous subarrays possible for every index by including the element at that index
Given a number N which represents the size of the array A[], the task is to find the number of contiguous subarrays that can be formed for every index of the array by including the element at that index in the original array. Examples: Input: N = 4 Output: {4, 6, 6, 4} Explanation: Since the size of
8 min read
Minimum bit flips such that every K consecutive bits contain at least one set bit
Given a binary string S, and an integer K, the task is to find the minimum number of flips required such that every substring of length K contains at least one '1'.Examples: Input: S = "10000001" K = 2 Output: 3 Explanation: We need only 3 changes in string S ( at position 2, 4 and 6 ) so that the s
8 min read
Sum of all subsequences of length K
Given an array arr[]and an integer K, the task is to find the sum of all K length subsequences from the given array. Example: Input: arr[] = {2, 3, 4}, K = 2 Output: 18 Explanation: There are 3 possible subsequences of length 2 which are {2, 3}, {2, 4} and {3, 4} The sum of all 2 length subsequences
6 min read