From 6ca41be67eeb4a60071afef529ba151f85792756 Mon Sep 17 00:00:00 2001 From: InstructorAnshul Date: Fri, 29 Nov 2019 15:51:08 +0530 Subject: [PATCH] Miscelleneous Problems Lectures added --- .../Miscelleneous Problems 12.md | 317 ++++++++++ .../Miscelleneous Problems 13.md | 569 ++++++++++++++++++ .../Miscelleneous Problems 14.md | 284 +++++++++ .../Miscelleneous Problems 15.md | 480 +++++++++++++++ .../Miscelleneous Problems 20.md | 366 +++++++++++ 5 files changed, 2016 insertions(+) create mode 100644 Miscelleneous Problems/Miscelleneous Problems 12.md create mode 100644 Miscelleneous Problems/Miscelleneous Problems 13.md create mode 100644 Miscelleneous Problems/Miscelleneous Problems 14.md create mode 100644 Miscelleneous Problems/Miscelleneous Problems 15.md create mode 100644 Miscelleneous Problems/Miscelleneous Problems 20.md diff --git a/Miscelleneous Problems/Miscelleneous Problems 12.md b/Miscelleneous Problems/Miscelleneous Problems 12.md new file mode 100644 index 0000000..8c06ba8 --- /dev/null +++ b/Miscelleneous Problems/Miscelleneous Problems 12.md @@ -0,0 +1,317 @@ +# Miscelleneous Problems 12 + +## 423 Good Graph + +### Problem Statement + +Given a directed graph of N nodes where each node is pointing to any one of the N nodes (can possibly point to itself). Ishu, the coder, is bored and he has discovered a problem out of it to keep himself busy. Problem is as follows: + +A node is ```'good' ```if it satisfies one of the following: + +``` +1. It is the special node (marked as node 1) +2. It is pointing to the special node (node 1) +3. It is pointing to a good node. +``` + +Ishu is going to change pointers of some nodes to make them all 'good'. You have to find the min. number of pointers to change in order to +make all the nodes good (Thus, a Good Graph). + +Note: Resultant Graph should hold the property that all nodes are good and each node must point to exactly one node. + +**Constraints:** + +``` +1 <= N <= 100,000 +``` + +**Input:** + +``` +A vector of N integers containing N numbers +all between 1 to N, where i-th number is +the number of node that i-th node is pointing to. +``` + +**Output:** + +``` +An Integer denoting min. number of pointer changes. +``` + +**Example:** + +```C++ +input: [1, 2, 1, 2] +output: 1 (Pointer of node 2 is made to point to node 1) + +input: [3, 1, 3, 1] +output: 1 (Pointer of node 3 is made to point to node 1) +``` + +### Wrong Approach +- Initialize count = 0. +- From every point do a BFS/DFS. If you can't reach any special node, increase count by 1. +- This approach will tell us the total number of non-good nodes. +- We can change the pointer in every good node. Thus we can say after count number of pointer changes we will have a good graph. +- This approach is wrong. Because there might a case like following: +```C++ +input: [1,2,1,2] +``` +- Here if we change the pointer of second element, we do not need to change the pointer of forth element. Thus we can say the minimum pointer change is 1. Here, the count of non-good nodes is two. +- How can we improve this approach? +### Brute Force +- For every node find the top most node that can reached from it. +- Save that node in a set. +- Return set.size() +### Hints +- We can see that if there is path from a node to a good node then it is a good node. +- If we can reach a good node from a given node we can mark it as good node. +- If we can not reach a good node from a given node, we will need at least one pointer change to make it good. +- If there is a chain like $5->4->3->2->4$. Now, if we change pointer of 4 to 1, all the nodes will become good. +- So, we can see again we just one pointer change to make the whole chain good. +- Let's color all the chains one by one. +- Since every node is only connected to at maximum one other node. BFS and DFS are same. It is similar to linked list traversal. + +```C++ +input: [1,2,2,3,4,5,7,7,8,9] + +Linked list representation: +1 +2<-2<-3<-4<-5<-6 +7<-7<-8<-9<-10 +``` + +### Code +```C++ +int Solution::solve(vector &A) { + + int n = A.size(); + bool good[n]; + good[0] = true; + for(int i = 1; i < n; i += 1){ + good[i] = false; + } + bool visited[n]; + for(int i = 0; i < n; i += 1){ + visited[i] = false; + } + int curr, next; + int ans = 0, c = 0; + int color[n]; + for(int i = 0; i < n; i += 1) { + if(visited[i] == false){ + curr = i; + visited[i] = true; + next = A[curr] - 1; + color[curr] = c; + while(visited[next] == false){ + good[curr] = true; + visited[next] = true; + color[next] = c; + curr = next; + next = A[curr] - 1; + } + if(color[next] == c && next != 0 ){ + ans += 1; + } + c += 1; + } + } + return ans; +} +``` +### Time Complexity +Since every node will be visited at max twice, the time complexity will be $O(n)$. + +### Dry Run +|Visited|Color|Good|i|A|count| +|:--|:--|:--|:--|:--|:--| +|[f,f,f,f,f,f]|[]|[t,f,f,f,f,f]|0|[1,2,2,5,6,3]|0| +|[t,f,f,f,f,f]|[0,]|[t,f,f,f,f,f]|1|[1,2,2,5,6,3]|0| +|[t,t,f,f,f,f]|[0,1]|[t,t,f,f,f,f]|2|[1,2,2,5,6,3]|1| +|[t,t,t,f,f,f]|[0,1,2]|[t,t,t,f,f,f]|3|[1,2,2,5,6,3]|1| +|[t,t,t,t,t,t]|[0,1,2,3,3,3]|[t,t,t,t,t,t]|4|[1,2,2,5,6,3]|1| +|All visited|||||| + + +[Good Graph](https://www.interviewbit.com/hire/test/problem/423/) + +## 438 King Graph + +### Problem +Kingdom JenaRajya is a well planned kingdom. They have N houses numbered [0,1,..,N-1] in the city and some bidirectional roads connecting the houses. King Jena has decided to meet his people and so he will visit one of the house in the kingdom where others can gather and meet him. King Jena is very kind and do not want anyone to travel far to meet him. So, he has come up with the following criteria to decide the house he will be visiting: + +Assuming that the people from other houses will take the shortest possible path to reach the house the king is visiting, King Jena wants to minimize the maximum distance one has to travel to meet him. In other words, he will choose the house where the shortest distance to the farthest house is minimum possible. + +Output the house number which King Jena will visit. + +**Note:** +1. In case there is a tie, he will visit the house with minimum house number. +2. You can assume that the graph is connected and so everyone will be able to visit. + +**Constraints:** +1 <= N <= 500 +1 <= Length of road <= 1000000 + +**Input format:** +Adjacency matrix representation of the graph. +A[i][j] = distance between house i and j. (A[i][i] = 0 and A[i][j] = -1, if house i and house j have no road between them) +As the roads are bidirectional, A[i][j] = A[j][i] + +**Example:** + +```C++ +Input: +A = [[0, 6, 8, -1], + [6, 0, 9, -1], + [8, 9, 0, 4], + [-1, -1, 4, 0]] + +Output: +2 +``` +### Brute Force +- We can run Dijkstra from each house to find the distance of every other house to this house. +- We can get a distance matrix for each node. +- Then we can find for every house the distance of the furtherest house from that house. +- Find the house which has minimum such distance. +- Time Complexity $O(V* ElogV)$ + +### Hint +- $E$ can be as big as $V^2$. The above brute force can take $O(V^3logV)$. +- We can reduce the time complexity by using Floyd Warsal all pair shortest path algorithm. +- Floyd Warsal will take only $O(V^3)$ time. This is not much better. However, the implementation is much simpler. +- Inductive Hypothesis + - Suppose that prior to the kth iteration it holds that for $i, j \in V$, $d_{ij}$ contains the length of the shortest path Q from i to j in G containing only vertices in the set ${1, 2, ..., k − 1}$ + - We can prove floyd warsal using this hypothesis. + +### Code +```C++ + +#define INF 1000000000 + +int Solution::solve(vector >& A){ + //No. of places + int n = A.size(); + + //Floyd-Warshall Algorithm implementation to find all pairs shortest paths + + vector > d(n,vector(n,INF)); + for(int i=0; i d[i][k]+d[k][j]) + d[i][j] = d[i][k]+d[k][j]; + + + //Find the required answer + int maxDist = -1, ans = -1, temp = INF; + for(int i=0; i &A, vector &B) +{ + vector moves(N+1, -1); + vector visited(N+1, false); + for(int i=0;i > que; + que.push(make_pair(1,0)); + pair entryExtracted ; + visited[1]=true; + while(!que.empty()) + { + entryExtracted = que.front(); + + if(entryExtracted.first==N) + break; + que.pop(); + for(int i=entryExtracted.first+1;i<=entryExtracted.first+6 && i<=N;i++) + { + pair entry; + if(!visited[i]) + { + entry.second = entryExtracted.second+1; + visited[i]=true; + if(moves[i]!=-1) + { + entry.first = moves[i]; + }else + entry.first =i; + + que.push(entry); + } + } + } + return entryExtracted.second; +} +``` \ No newline at end of file diff --git a/Miscelleneous Problems/Miscelleneous Problems 13.md b/Miscelleneous Problems/Miscelleneous Problems 13.md new file mode 100644 index 0000000..cd9cb49 --- /dev/null +++ b/Miscelleneous Problems/Miscelleneous Problems 13.md @@ -0,0 +1,569 @@ +# Miscelleneous Problems 13 + +## Game Of Ways + +### Problem Statement + +Batman is about to take off from Gotham’s airport which has m runways(numbered from 1 to m) of length n units. +As always, the Joker has come up with an insane game to have fun with Batman. + + +The rules of the game are as follows:: + + - Batman’s plane can take off only after running for n-units distance in the runways. + - Batman can start on any runway and end on any runway. + - Batman can switch his plane from runway i to j only if i and j are coprime. + - If the batman fails to switch his plane to a coprime runway, after running for 1 unit distance on a single runway, the Joker will bomb the plane. + +The Joker does not want to kill the batman, because what will he do without him. So he asks for your help to find out number of ways in which Batman can take off his plane without getting bombed. + +As the answer can be very large, output answer modulo (1000000007) + +---------- + +**Input Format** +``` +First argument given is an Integer A, Length of the runway. +Second argument given is an Integer B, +Number of different runways available +``` + + +**Output Format** +``` +Return a single integer X, the number of ways Batman can take off his plane without getting bombed. +As X can be very large, return X MOD 10^9+7 +``` +**Constraints** +``` +1 <= A <= 1000000000 +0 <= B <= 10 +``` +**For Example** +```C++ +Input 1: + A = 1 + B = 3 + Output 1: + 3 + +Input 2: + A = 2 + B = 3 + Output 1: + 7 + +Explanation: + For test 1: + 3 Ways Starting at 1, 2, 3 + + For test 2: + 1st way: starting and covering whole distance at runway 1. + i.e 1 -> 1 (1 and 1 are co-prime so Batman can continue on + runway 1 without getting bombed) + 2nd way: starting and covering distance of 1 at runway 1 + and covering remaining distance at runway 2. i.e 1 -> 2 + 3rd way: starting and covering distance of 1 at runway 1 + and covering remaining distance at runway 3. i.e 1 -> 3 + similarly there are 4 more ways i.e 2 -> 1, 2 -> 3, 3 -> + 1, 3 -> 2 + + we can't go from 2 -> 2 and 3 -> 3 as per given rules. +``` +### Brute force +- Generate all permutations of 1,...,B of size A. +- Check if all the consicutive elements are co-prime. Count all such permutations. +- Time Complexity: B^A. + +### First Approach +- It should be clear from the question that we need a graph of size B. +- Let's apply dynamic programing on this graph. +- Let dp[i][k] be the number of ways to start at i and run a length of k. +- dp[i][1] = 1 for all i. +- $dp[i][k] = \sum_{j \in adj[i]}dp[j][k-1]$ + +**Code** +```C++ +int gcd(int i, int j){ + if(i>j) return gcd(j,i); + else if (i == 0) return j; + else{ + int k = j%i; + return gcd(k, i); + } +} + +bool coPrime(int i, int j){ + return gcd(i,j) == 1; +} +void printArray(vector> adj){ + for(int i = 0 ; i> adj(B); + for(int i = 0; i< B; ++i){ + for(int j = i ; j dp_old(B); + vector dp_new(B); + for(int i = 0; i < B; ++i){ + dp_new[i] = 1; + } + int mod = 1000000007; + for(int k = 2; k<=A; ++k){ + dp_old = dp_new; + for(int i = 0; i< B; ++i){ + dp_new[i] = 0; + for(auto j : adj[i]){ + dp_new[i] += dp_old[j]%mod; + dp_new[i] %= mod; + } + } + } + int res= 0; + for(int i= 0; ij) return gcd(j,i); + else if (i == 0) return j; + else{ + int k = j%i; + return gcd(k, i); + } +} + +bool coPrime(int i, int j){ + return gcd(i,j) == 1; +} +void printArray(vector> adj){ + for(int i = 0 ; i> &A, vector> &B){ + int n = A.size(); + for(int i= 0; i> &A){ + int n = A.size(); + vector> temp(n, vector(n)); + copy(A,temp); + for(int i = 0; i> &A, vector> &B){ + int n = A.size(); + vector> temp(n, vector(n)); + copy(A,temp); + for(int i = 0; i> A){ + cout << "-------------" << endl; + for(auto row: A){ + for(auto cell: row){ + cout << cell << " " ; + } + cout << endl; + } +} +void pow_matrix(vector> &adj,int A, vector> &orignal){ + //print(adj); + //cout << A << endl; + if(A == 1) return; + int n = adj.size(); + pow_matrix(adj, A/2, orignal); + square(adj); + if(A%2 == 1){ + multiply(adj, orignal); + } +} + +int Solution::solve(int A, int B) { + if(A == 0) return 0; + if(A == 1) return B; + vector > adj(B, vector (B,0)); + for(int i = 0; i< B; ++i){ + for(int j = 0 ; j> identity(n, vector(n,0)); + copy(adj,identity); + pow_matrix(adj, A-1, identity); + long long int sum = 0; + for(int i= 0; i A[i+1]$ + - $A[j] > A[j+1]$ +- We fill all the nodes after j to level of j. And fill nodes after $i$ like the first case. + +### Code + +```C++ +bool isValid(vector psum, int i, int X, int Y, int h){ + long long sum = psum[X] - psum[i]; + return h*(X-i) - sum <= Y; +} +void update(vector &array, int X, int Y){ + int n = array.size(); + vector psum(n,0); + psum[0] = array[0]; + for(int i=1; i 0){ + array[i]++; + Y--; + remaining--; + } + } + return; +} +vector Solution::solve(int A, vector > &B) { + vector array(A,0); + for(auto b : B){ + update(array, b[0]-1, b[1]); + } + return array; +} +``` +### Time Complexity +- Since we are running a loop of size $O(X)$ twice for every update, $O(X* T)$. + +## Sum of Inversions + +### Problem Statement + +Consider a random permutation P of numbers [1, 2, .., N]. This permutation is called special if there is no element P[i] in P such that **P[i] = i+1** (Consider 0 based indexing). In other words, a permutation is special if it is a derangement (no number is at its "natural" (ordered) place). + +Given a number N, find the sum of inversions in all the special permutations of numbers [1, 2, ..., N] modulo **1000000007**. An inversion in an array P is a pair P[i], P[j] such that P[i] > P[j] and i rank in iteration i=3 in for loop is 1 which means + // there is 1 number in the mask less than 4 (and that number is 2 in this case) + rank += 1; + } + } +``` +### Hints on Website +This type of problems requires a special DP formulation known as Bitmask DP. Those who are not familiar with the concept are advised to Google it before proceeding further. + +Consider the following DP formulation: + +mask = bitmask where i-th set bit from the left means number i is yet to be used in generating a special permutation. +e.g.: mask = 5 => mask = 101 (binary) => Current permutation 2 _ _. Use numbers [1,3] to fill the blanks in the current permutation. + +cnt = no. of unset bits in mask (mask = 5 => mask = 101 (binary) => no. of unset bits = 1) + +dp[mask] = sum of inversions of all the special permutations that can be generated using the numbers corresponding to set bits in mask such that the numbers should be arranged at positions [cnt+1, cnt+2, .., N] + +e.g.: +mask = 101 +One number is already fixed at position 1 and that number is 2. Permutation generated till this point is 2 _ _. Now we have to arrange the remaining numbers [1,3] at blank positions and form a special permutation. + +Recursion tree for N = 3 looks like following: + +``` + 111 + / | \ + 011(1__) 101(2__) 110(3__) + / \ / \ + 001 100 100 010 + (21_) (23_) (32_) (31_) +``` + +Here, 011 at level 2 in the tree is not extended further as it is not a valid permutation (011 corresponds to permutation 1 _ _ and 1 cannot be at its correct position according to our rule of special permutations). Similarly "100" (child of "110" in level 3) is also not a valid permutation as that corresponds to permutation 32_. +This type of formulation will require us to ignore the branches of tree that form a non-valid permutation and consider those which forms a valid permutation. Now, the only challenge is to count the sum of inversions at every node of the tree. This is left as an exercise to the reader. Coding part is very easy once you have thought of a way to augment the recursion tree to store necessary information. + +Time complexity of this approach would be O(C*N*(2^N)) which is much less than O(N!). + +For any given N, our answer is simply dp[(1< rank in iteration i=3 in for loop is 1 which means + // there is 1 number in the mask less than 4 (and that number is 2 in this case) + rank += 1; + } + } + + dp[mask].vis = 1; + + return dp[mask]; +} + +int Solution::solve(int n){ + int mask = (1< 111...1 "n ones" + +for(int i=0; i< (1< A : A[i] --> Parent of node number i+1. + (A[2] = 1 means parent of node number 3 is 1). +vector B : value[i] --> value associated with + node number i+1. + +Note: Parent of node number 1 is 0 (A[0] = 0). +``` +**Output:** +A number containing the maximum possible sum. +`(As the answer can be large, output the answer modulo 1000000007)` + +**Example:** + +``` +Input: +A : [0, 1, 1, 1, 3, 3, 6, 6] +B: [1, 2, 3, 4, 5, 100, 7, 8] + +Output: +111 +Node number 2, 4, 5 and 6 are chosen. Sum = 2 + 4 + 5 + 100 = 111 +``` +### Brute Force +- The absolute brute force would be to take every subset. +- Check if it contains a child-parent or grandchild-grandparent relationship. +- Maximize the sum of values among these subsets. + +### Hints +- Can we optimize the above brute force? +- We can select the node only if its child and grandchild are not selected. +- Can we reduce this problem to an array problem? That array problem will look as follows: + - You are given an array. There is a value stored at every cell. You need to find a subset with highest value sum. If you include A[i] into the set, you cannot include A[i-2], A[i-1], A[i+1], and A[i+2] into the set. +- The above problem can be solved using Dynamic Programming. + - We can store, for all index i, the maximum value of a valid subset of A[0..i]. + - $dp[i] = max(dp[i-3]+A[i], dp[i-1])$ + - We just look at $dp[i-3]$ and $dp[i-1]$ as $dp[i-2]$ is already included in $dp[i-1]$. +- Can we apply a similar approach to our tree problem? + +### Code +```C++ +#define ll long long int +int mod = 1000000007; +int getMaxDP(int node, vector> &child, vector> &ggchild, vector &dp, vector &value){ + if(dp[node] != -1) return dp[node]; + int first = 0, second = 0; + first = value[node]%mod; + for(auto ggc: ggchild[node]){ + first = (first%mod + getMaxDP(ggc,child,ggchild,dp,value)%mod)%mod; + } + for(auto c: child[node]){ + second = (second%mod + getMaxDP(c,child,ggchild,dp,value)%mod)%mod; + } + return max(first, second); +} +int Solution::solve(vector &A, vector &B) { + int n = A.size(); + vector> adj(n); + vector> ggchild(n); + vector dp(n,-1); + for(int i = 1; i s; + for(int i = 0; i < A; ++i){ + s.insert(doubleB.substr(i,A)); + } + return *s.begin(); +} +``` +### Time Complexity +- Each string comparision may take $O(n)$ time. Here, $n$ is the length of string. +- We have to compare strings $O(n)$ times. Thus the total time complexity will be $O(n^2)$. +- If we use a set, the time complexity will be $O(n^2\log{n})$. This is because insertion in set will take $O(n\log{n})$ time. + +## Ways to Arrange Two Objects + +### Problem Statement +You are given two types of objects : A and B. There is an infinite supply of both the type of objects . +All the objects of type A are identical and same is the case with all the objects of type B. + +Given two integers N and L, find the number of ways in which you can arrange the N objects such that you don't have L or more +consecutive objects of type A together. + +**Constraints:** + +``` +1 < N < 100001 + +1 < L < 100001 + +1 < N*L < 100001 +``` + +**Input Format** + +``` + +Input consists on one line containing the value of N and L. +``` + +**Output Format** + +``` +Return number of ways modulo 10^9 + 7 +``` + +**Example:** + +``` +Input:4 2 + +Output: 8 + +Explanation: + +{B,B,B,B} + +{B,B,B,A} + +{B,B,A,B} + +{B,A,B,B} + +{A,B,B,B} + +{A,B,A,B} + +{A,B,B,A} + +{B,A,B,A} +``` +### Brute Force +- We can consider all the possible arrangements of A and B. +- For each arrangement, we can check if there are L consicutive A's. We can neglect those arrangements and count others. +- This approach will take $O(n * 2^n)$ time. + +### Hints +- We can neglact some arrangements even before making them if at each i we keep count of consecutive A's ending at i. +- Suppose there are L-1 A's ending at i. For example L = 3 and N = 6 and i = 3 + - ${B, A, A}$ now on the next step we can not include A. +- Can we memoize these states in dp? + +### Solution +- Dp state: dp[i][j] number of arrangements of A and B of length i with j consicutive A's towards the end. +- $dp[i][0]=\sum_{k\in{[0,L-1]}}dp[i-1][k]$ +- $dp[i][j]_{j>0} = dp[i-1][j-1]$ +### Code +```C++ +int mod = 1000000007; +int Solution::solve(int A, int B) { + vector> dp(A+1, vector(B,0)); + dp[0][0] = 1; + for(int i = 1; i <= A; ++i){ + for(int j = 0; j< B; ++j){ + if(j == 0){ + int val = 0; + for(int k = 0; k|0|1| +|:--|:--|:--| +|i = 0|1|0| +|1|1|1| +|2|2|1| +|3|3|2| +|4|5|3| +|Answer| 8|| \ No newline at end of file diff --git a/Miscelleneous Problems/Miscelleneous Problems 15.md b/Miscelleneous Problems/Miscelleneous Problems 15.md new file mode 100644 index 0000000..b89d76f --- /dev/null +++ b/Miscelleneous Problems/Miscelleneous Problems 15.md @@ -0,0 +1,480 @@ +# Miscelleneous Problems 15 +## Bits and Bytes +### Problem Statement +You are given a binary string **S**. + +You process it through a series of operations starting from the left where: + 1) In the first operation, you remove the first bit of the number and append it to the right. + 2) In the second operation, you remove the first 2 bits of the processed string one by one and append them to the right. + 3) In the third operation, you now remove the first 3 bits of the new string one by one and append them to the right. + 4) In the ith operation, you remove the first i bits of the new string one by one and append them to the right. + +You have to find the minimum number of operations it takes to get back the original string. + +Number of operations cannot be 0. + +**Constraints:** + +``` +1 <= length of S <= 10^5 +``` + +**Input:** + +``` +S : Binary string +``` + +**Output:** + +``` +Minimum number of operations to get back the +original string. +``` + +**Example:** + +``` +Input: +S: 111 + +Output: +1 + +In the first operation, the leftmost bit (1) +gets appended to the end of the string, and you +get the same string as the original, hence +answer is 1. + +Input: +S: 101 + +Output: +2 + +In the first operation, the leftmost bit (1) +gets appended to the end of the string, and you +get the string 011. + +In the second operation, the 2 leftmost bits get +appended to the end (011 => 110 => 101), we get +the same string as the original, hence answer is +2. + +``` +### Brute Force +- For every i from 1 to $\infty$, We can rotate the string by i digits and check if the new string is same as the original string. +- Time Complexity, We may run into an infinity loop. +- Suppose we can be sure that we will get our result in $O(n)$. For every i we will need $O(n)$ time. So, the total time will be $O(n^2)$. + +### Hints +- We can see that by $i^{th}$ operation we will have rotated $\frac{i*(i+1)}{2}$ times. Let's call this $T_i$. +- If for some $i$, $T_i$ is divisible by $len(s)$, we can say we will definetely get our string back. +- For $i = 2* len(s)-1$, $T_i$ will obviously be divisible by $len(s)$. +- So, we can run a loop from $1$ to $2* len(s) -1$ on $i$. And check if $T_i$ will be divisible by $len(s)$ or not. +- This will run in $O(n)$ time. +- Will it give the smallest such i? +- The string may have a pattern repeating over and over again. For example : $s=101101101$, answer will be $2$. +- Can we find the length of the shortest repeating sequence? We can use KMP algorithm to do that. +- What will be the lps of above string? Answer: $LPS = [001123456]$. +- If $len(s)-LPS[len(s)-1]$ divides $len(s)$, $len(s)-LPS[len(s)-1]$ is the length of the repeating sequence. +- Now, we have to match $T_i$ with length of repeating pattern if there is a repeating pattern. + +### Code +```C++ +typedef long long ll; + +ll minLEN(string s,ll lps[]){ + lps[0]=0; + ll len=0; + ll p=1; + while(p &B, string C) { + ll n,use; + n=A;ll arr[n+1]; + // cin>>use; + for(ll i=1;i<=n;i++) + { + arr[i]=B[i-1]; + } + string s,ans; + s=C; + ll pref[n]; + pref[1]=s[0]-'0'; + for(ll i=2;i buffer){ + k-=buffer; + continue; + } + if(i == f) return to_string(i) + function_two(rem, k); + return to_string(i) + function_two(to_string(9*(temp/10)), k); + } + +} + +/* +function_one(n,k) computes the first +digit of the kth required number. +function_one and function_two are +separate as 1st digit can't be zero whereas +rest of the digits can be zero. +*/ +string function_one(string s, int k){ + + int l = s.size(); //length of the number + int f = s[0]-'0'; //first digit of the number + int temp = stoi(string(l,'1')); // 1111111... l digits + + //Base case, only 1 digit number + if(l==1) return to_string(k); + + //Utility string, used below in the for loop + string rem = s.substr(1); + + //find the number of numbers say + //num starting from x (x <= i). + //if k > num, first digit is not i, + //else first digit is i. + + //Note that i here starts from 1. + for(int i=1; i<10; i++){ + //Here we calculate the number of + //numbers starting from i. + //There will be multiple cases + //to handle which becomes clear + //after a little thinking. + + if(i == f) temp/=10; + int buffer = temp; + if(i == f) buffer += stoi(rem) + 1; + + if(k > buffer){ + k-=buffer; + continue; + } + if(i == f) return to_string(i) + function_two(rem, k); + return to_string(i) + function_two(to_string(9*(temp/10)), k); + } +} + + + +vector Solution::solve(int A,const vector &B){ + string str = to_string(A); + + int m = B.size(); + vector ans(m); + + //function_one(n,k) give kth + //number in the sorted order of strings ["1", "2", ..., "n"] + for(int i=0; i +#include +#include +#include +#include +#define lli long long +#define MAX 10004 +#define INF 10000000000000000LL +using namespace std; +int mx; +lli A[MAX]; +int val[MAX]; +bool vis[MAX][1024]; +lli dp[MAX][1024]; +int n; +void validate(string s) +{ + int sz = (int)s.size(); + assert(sz == 10); + for ( int i = 0; i < 10; i++ ) assert(s[i] == '0' || s[i] == '1'); +} +lli f(int idx, int mask) +{ + if ( idx == n ) { + if ( __builtin_popcount(mask) == mx ) return 0; + return INF; + } + if ( vis[idx][mask] ) return dp[idx][mask]; + vis[idx][mask] = true; + lli ans = min(f(idx + 1, mask), A[idx] + f(idx + 1, mask | val[idx])); + dp[idx][mask] = ans; + return ans; +} +int main() +{ + freopen("inp5.txt", "r", stdin); + freopen("out5.txt", "w", stdout); + string s; + set distinctBalls; + cin >> n; + assert(n >= 1 && n <= 10000); + for ( int i = 0; i < n; i++ ) { + cin >> A[i]; + cin >> s; + assert(A[i] >= 0 && A[i] <= 1000000000); + validate(s); + for ( int j = 0; j < 10; j++ ) { + if ( s[j] == '1' ) distinctBalls.insert(j), val[i] |= (1 << j); + } + } + mx = (int)distinctBalls.size(); + cout << f(0, 0) << endl; + return 0; +} +``` +### Time Complexity +- Since we are calculating the every dp state only once. The time complexity will be $O(n \times 2^{10})$. + +### Dry Run +- Let's say we have only two colors. +- N = 3 +- A = {5, 10, 20} +- B = {10, 01, 11} +|Mask|Index|Dp|Expression(min)| +|:--|:--|:--|:--| +|00|0|15 |dp[1][00],A[0](=5) + dp[1][10]| +|00|1|20 |dp[2][00],A[1](=10) + dp[2][01]| +|10|1|10 |dp[2][10],A[1](=10) + dp[2][11]| +|00|2|20 |dp[3][00],A[2](=20) + dp[3][11]| +|01|2|20 |dp[3][01],A[2](=20) + dp[3][11]| +|10|2|20 |dp[3][10],A[2](=20) + dp[3][11]| +|11|2|0 |dp[3][11],A[2](=20) + dp[3][11]| +|00|3|INF|| +|01|3|INF|| +|10|3|INF|| +|11|3|0| | + + +## The Ghost Type + +### Problem Statement +Gengar has got an integer **A**. Now using his ghostly powers, he can create the permutation from **1** to **A** of this given number. + +Since, he's a special kind of Poke'mon, so he thinks he deserves special permutations. He wants to find the total number of special permutations of length **N**, consisting of the integers from **1** to **A**. + +A permutation is called special if it satisfies following condition: + +If **Px & Py == Px**, then **x** < **y**, where **x** and **y** are two distinct indices of permutation and **P** is the permutation itself. "**&**" denotes the bitwise and operation. + +Help Gengar in finding the number of such permutations. + +**Input Format:** +``` + First and only argument of + input conatins a single integer A +``` +**Output Format:** + + Ouput a string denoting the answer. + +**Constraints:** + + 1 <= A <= 20 + +**For Example:** +``` +Example Input 1: + A = 3 +Example Output 1: + 2 +Explanation 1: + Special Permutation are: [1, 2, 3] and [2, 1, 3] +Example Input 2: + A = 4 +Example Output 2: + 8 +``` +### Brute Force +- Given a permutation we can check in $O(n^2)$ time whether it is special or not. +- We can consider all the permutations of $1...A$. Then we can count special permutations. +- This approach will take $O(2^n \times n^2)$. +### Hints +- If we look at a subset of numbers which are already there in the permutation from $1...i$, we can choose the next number to include. +- Next element to include will be one whose all x's are included. +- Thus if we start from an empty subset, we can build the complete set in buttom up manner. +### Code +```C++ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +using namespace std; +#define rep(i,n) for(int i=0;i +#define pii pair +#define f first +#define mp make_pair +#define mod 1000000007 +#define s second +#define pb push_back +vectorsubmask[22]; +bool vis[1<<22]; +ll dp[1<<22]; +int N; +ll rec(int mask){ + if(mask==(1<<(N+1))-2) return 1; + if(vis[mask]) return dp[mask]; + vis[mask] = 1; + ll &ret = dp[mask]; + ret=0; + int x; + for(int i=1;i<=N;i++){ + if(!(mask&(1<=1;j--){ + if( (i&j)==j ) submask[i].pb(j); + } + } + cin >> N; + cout< 9 + 2 -> 4 + 3 -> 4 + --------- + 17 +``` \ No newline at end of file