📌  相关文章
📜  长度为N的二进制字符串的计数,最多具有M个连续的1或0,或者正好是K次

📅  最后修改于: 2021-06-25 14:50:40             🧑  作者: Mango

给定三个整数N,KM。任务是找出始终以1开头的长度为N二进制字符串的数量,其中最多可以有M个连续的1或0,它们正好交替K次。
例子:

方法:由于此问题涉及重叠子问题和最佳子结构。因此,可以使用动态编程解决此问题。

  • 子问题DP [i] [j]代表到现在为止具有j个交替组的长度为i的二进制字符串的数量。因此,如果我们知道dp [nj] [k-1]的值,则要计算dp [N] [K],则可以通过将j = 1到m(DP(DP) [N] [K]代表最终答案)。
    如下所示,在递归树图中,观察到许多子问题重叠。因此,需要对结果进行缓存以避免冗余计算。

  • 最佳子结构:
    $dp[i][j]=$$\sum_{j=1}^{M} f(N-j, K-1)
  • 通过遵循自上而下的DP方法:
    因为我们可以有一个最大为M的组,所以我们在每个可能的长度上进行迭代,并使用新的N递归,并随着新的K的形成将K减1。对子问题的解决方案进行缓存并加总以得出最终结果dp [N] [K]。
  • 基本情况:
    1. 当N为0且K为0时,则返回1
    2. 当N为0但K不为0时,则返回0
    3. 当N不为0但K为0时,则返回0
    4. 当两者均为负数时,返回0

下面是上述方法的实现:

C++
// C++ program to find the count
// of Binary strings of length N
// having atmost M consecutive 1s or 0s
// alternatively exactly K times
 
#include 
using namespace std;
 
// Array to contain the final result
int dp[1000][1000];
 
// Function to get the number
// of desirable binary strings
int solve(int n, int k, int m)
{
 
    // if we reach end of string
    // and groups are exhausted,
    // return 1
    if (n == 0 && k == 0)
        return 1;
 
    // if length is exhausted but
    // groups are still to be made,
    // return 0
    if (n == 0 && k != 0)
        return 0;
 
    // if length is not exhausted
    // but groups are exhausted,
    // return 0
    if (n != 0 && k == 0)
        return 0;
 
    // if both are negative
    // just return 0
    if (n < 0 || k < 0)
        return 0;
 
    // if already calculated,
    // return it
    if (dp[n][k])
        return dp[n][k];
 
    // initialise answer
    // for each state
    int ans = 0;
 
    // loop through every
    // possible m
    for (int j = 1; j <= m; j++) {
        ans += solve(n - j, k - 1, m);
    }
    return dp[n][k] = ans;
}
 
// Driver code
int main()
{
 
    int N = 7, K = 4, M = 3;
    cout << solve(N, K, M);
}


Java
// Java program to find the count of
// Binary Strings of length N having
// atmost M consecutive 1s or 0s
// alternatively exactly K times
import java.util.*;
 
class GFG{
 
// Array to contain the final result
static int [][]dp = new int[1000][1000];
 
// Function to get the number
// of desirable binary strings
static int solve(int n, int k, int m)
{
 
    // If we reach end of string
    // and groups are exhausted,
    // return 1
    if (n == 0 && k == 0)
        return 1;
 
    // If length is exhausted but
    // groups are still to be made,
    // return 0
    if (n == 0 && k != 0)
        return 0;
 
    // If length is not exhausted
    // but groups are exhausted,
    // return 0
    if (n != 0 && k == 0)
        return 0;
 
    // If both are negative
    // just return 0
    if (n < 0 || k < 0)
        return 0;
 
    // If already calculated,
    // return it
    if (dp[n][k] > 0)
        return dp[n][k];
 
    // Initialise answer
    // for each state
    int ans = 0;
 
    // Loop through every
    // possible m
    for(int j = 1; j <= m; j++)
    {
       ans += solve(n - j, k - 1, m);
    }
    return dp[n][k] = ans;
}
 
// Driver code
public static void main(String[] args)
{
    int N = 7, K = 4, M = 3;
    System.out.print(solve(N, K, M));
}
}
 
// This code is contributed by Rajput-Ji


Python 3
# Python3 program to find the count
# of Binary strings of length N
# having atmost M consecutive 1s or
# 0s alternatively exactly K times
 
# List to contain the final result
rows, cols = (1000, 1000)
dp = [[0 for i in range(cols)]
         for j in range(rows)]
 
# Function to get the number
# of desirable binary strings
def solve(n, k, m):
     
    # If we reach end of string
    # and groups are exhausted,
    # return 1
    if n == 0 and k == 0:
        return 1
 
    # If length is exhausted but
    # groups are still to be made,
    # return 0
    if n == 0 and k != 0:
        return 0
 
    # If length is not exhausted
    # but groups are exhausted,
    # return 0
    if n != 0 and k == 0:
        return 0
 
    # If both are negative
    # just return 0
    if n < 0 or k < 0:
        return 0
 
    # If already calculated,
    # return it
    if dp[n][k]:
        return dp[n][k]
 
    # Initialise answer
    # for each state
    ans = 0
 
    # Loop through every
    # possible m
    for j in range(1, m + 1):
        ans = ans + solve(n - j,
                          k - 1, m)
    dp[n][k] = ans
     
    return dp[n][k]
 
# Driver code
N = 7
K = 4
M = 3
 
print(solve(N, K, M))
 
# This code is contributed by ishayadav181


C#
// C# program to find the count of
// binary strings of length N having
// atmost M consecutive 1s or 0s
// alternatively exactly K times
using System;
 
class GFG{
 
// Array to contain the readonly result
static int [,]dp = new int[1000, 1000];
 
// Function to get the number
// of desirable binary strings
static int solve(int n, int k, int m)
{
 
    // If we reach end of string
    // and groups are exhausted,
    // return 1
    if (n == 0 && k == 0)
        return 1;
 
    // If length is exhausted but
    // groups are still to be made,
    // return 0
    if (n == 0 && k != 0)
        return 0;
 
    // If length is not exhausted
    // but groups are exhausted,
    // return 0
    if (n != 0 && k == 0)
        return 0;
 
    // If both are negative
    // just return 0
    if (n < 0 || k < 0)
        return 0;
 
    // If already calculated,
    // return it
    if (dp[n, k] > 0)
        return dp[n, k];
 
    // Initialise answer
    // for each state
    int ans = 0;
 
    // Loop through every
    // possible m
    for(int j = 1; j <= m; j++)
    {
       ans += solve(n - j, k - 1, m);
    }
    return dp[n, k] = ans;
}
 
// Driver code
public static void Main(String[] args)
{
    int N = 7, K = 4, M = 3;
     
    Console.Write(solve(N, K, M));
}
}
 
// This code is contributed by gauravrajput1


Javascript


输出:
16

时间复杂度: O(N * K * M)

如果您希望与行业专家一起参加现场课程,请参阅《 Geeks现场课程》和《 Geeks现场课程美国》。