📜  a ^ ib ^ jc ^ k形式的子序列数

📅  最后修改于: 2021-04-24 19:40:34             🧑  作者: Mango

给定一个字符串,计数形式为a i b j c k的子序列,即由i’a’个字符,后跟j’b’个字符,后跟k个’c’个字符,其中i> = 1, j> = 1且k> = 1。
注意:如果为两个子序列选取的数组索引的集合不同,则认为两个子序列是不同的。
预期时间复杂度:O(n)
例子:

Input  : abbc
Output : 3
Subsequences are abc, abc and abbc

Input  : abcabc
Output : 7
Subsequences are abc, abc, abbc, aabc
abcc, abc and abc

方法:
我们遍历给定的字符串。对于每次遇到的字符,我们都会执行以下操作:
1)初始化由“ a”的不同组合引起的不同子序列的计数。让此计数为aCount。
2)初始化由“ b”的不同组合引起的不同子序列的计数。将此计数设为bCount。
3)初始化由“ c”的不同组合引起的不同子序列的计数。将此计数设为cCount。
4)遍历给定字符串的所有字符。对当前字符s [i]执行以下操作
如果当前字符为’a’ ,则存在以下可能性:
a)当前字符开始一个新的子序列。
b)当前字符是aCount子序列的一部分。
c)当前字符不是aCount子序列的一部分。
因此我们做aCount =(1 + 2 * aCount);
如果当前字符为’b’ ,则存在以下可能性:
a)当前字符以aCount子序列开始b的新子序列。
b)当前字符是bCount子序列的一部分。
c)当前字符不属于bCount子序列。
因此我们做bCount =(aCount + 2 * bCount);
如果当前字符为’c’ ,则存在以下可能性:
a)当前字符以bCount子序列开始c的新子序列。
b)当前字符是cCount子序列的一部分。
c)当前字符不属于cCount子序列。
因此我们做cCount =(bCount + 2 * cCount);
5)最后我们返回cCount;
借助示例对方法进行说明:

  • aCount是字母“ a”的子序列数。
  • 考虑以下示例:aa。
  • 我们可以看到aCount为3,因为我们可以选择以下可能性:(xa,ax,aa)(x表示我们没有使用该字符)。还请注意,这与两者之间的字符无关,即aaa和ccbabbbcac的aCount相同,因为它们都恰好有2个a。
  • 现在,加上1 a,我们现在有以下新的子序列:每个旧的子序列,每个旧的子序列+新的a和新的字母a。因此共有aCount + aCount + 1个子序列。
  • 现在,让我们考虑bCount,即先后包含一些a和随后一些b的子序列数。在“ aab”中,我们看到bCount应该为3(axb,xab,aab),因为这只是我们选择前两个a的子序列,然后选择b的子序列的方法数量。因此,每次我们添加ab时,路数都会增加aCount。
  • 让我们为“ aabb”找到bCount。我们已经确定aab具有3个子序列,因此我们当然仍然具有这些子序列。另外,我们可以将新的b添加到这些子序列中的任何一个上,以获得3个以上的子序列。最后,我们必须计算在不使用任何其他b的情况下产生的子序列,根据上一段中的逻辑,这只是一个aCount。因此,此后的bCount只是旧的bCount * 2 + aCount;
  • cCount相似。

下面是上述想法的实现:

C++
// C++ program to count subsequences of the
// form a^i b^j c^k
#include 
using namespace std;
 
// Returns count of subsequences of the form
// a^i b^j c^k
int countSubsequences(string s)
{
    // Initialize counts of different subsequences
    // caused by different combination of 'a'
    int aCount = 0;
 
    // Initialize counts of different subsequences
    // caused by different combination of 'a' and
    // different combination of 'b'
    int bCount = 0;
 
    // Initialize counts of different subsequences
    // caused by different combination of 'a', 'b'
    // and 'c'.
    int cCount = 0;
 
    // Traverse all characters of given string
    for (unsigned int i = 0; i < s.size(); i++) {
        /* If current character is 'a', then
           there are the following possibilities :
             a) Current character begins a new
                subsequence.
             b) Current character is part of aCount
                subsequences.
             c) Current character is not part of
                aCount subsequences. */
        if (s[i] == 'a')
            aCount = (1 + 2 * aCount);
 
        /* If current character is 'b', then
           there are following possibilities :
             a) Current character begins a new
                subsequence of b's with aCount
                subsequences.
             b) Current character is part of bCount
                subsequences.
             c) Current character is not part of
                bCount subsequences. */
        else if (s[i] == 'b')
            bCount = (aCount + 2 * bCount);
 
        /* If current character is 'c', then
           there are following possibilities :
             a) Current character begins a new
                subsequence of c's with bCount
                subsequences.
             b) Current character is part of cCount
                subsequences.
             c) Current character is not part of
                cCount subsequences. */
        else if (s[i] == 'c')
            cCount = (bCount + 2 * cCount);
    }
 
    return cCount;
}
 
// Driver code
int main()
{
    string s = "abbc";
    cout << countSubsequences(s) << endl;
    return 0;
}


Java
// Java program to count subsequences of the
// form a^i b^j c^k
public class No_of_subsequence {
 
    // Returns count of subsequences of the form
    // a^i b^j c^k
    static int countSubsequences(String s)
    {
        // Initialize counts of different subsequences
        // caused by different combination of 'a'
        int aCount = 0;
 
        // Initialize counts of different subsequences
        // caused by different combination of 'a' and
        // different combination of 'b'
        int bCount = 0;
 
        // Initialize counts of different subsequences
        // caused by different combination of 'a', 'b'
        // and 'c'.
        int cCount = 0;
 
        // Traverse all characters of given string
        for (int i = 0; i < s.length(); i++) {
            /* If current character is 'a', then
               there are following possibilities :
                 a) Current character begins a new
                    subsequence.
                 b) Current character is part of aCount
                    subsequences.
                 c) Current character is not part of
                    aCount subsequences. */
            if (s.charAt(i) == 'a')
                aCount = (1 + 2 * aCount);
 
            /* If current character is 'b', then
               there are following possibilities :
                 a) Current character begins a new
                    subsequence of b's with aCount
                    subsequences.
                 b) Current character is part of bCount
                    subsequences.
                 c) Current character is not part of
                    bCount subsequences. */
            else if (s.charAt(i) == 'b')
                bCount = (aCount + 2 * bCount);
 
            /* If current character is 'c', then
               there are following possibilities :
                 a) Current character begins a new
                    subsequence of c's with bCount
                    subsequences.
                 b) Current character is part of cCount
                    subsequences.
                 c) Current character is not part of
                    cCount subsequences. */
            else if (s.charAt(i) == 'c')
                cCount = (bCount + 2 * cCount);
        }
 
        return cCount;
    }
 
    // Driver code
    public static void main(String args[])
    {
        String s = "abbc";
        System.out.println(countSubsequences(s));
    }
}
// This code is contributed by Sumit Ghosh


Python 3
# Python 3 program to count
# subsequences of the form
# a ^ i b ^ j c ^ k
 
# Returns count of subsequences
# of the form a ^ i b ^ j c ^ k
def countSubsequences(s):
 
    # Initialize counts of different
    # subsequences caused by different
    # combination of 'a'
    aCount = 0
 
    # Initialize counts of different
    # subsequences caused by different
    # combination of 'a' and different
    # combination of 'b'
    bCount = 0
 
    # Initialize counts of different
    # subsequences caused by different
    # combination of 'a', 'b' and 'c'.
    cCount = 0
 
    # Traverse all characters
    # of given string
    for i in range(len(s)):
     
        # If current character is 'a',
        # then there are following
        # possibilities :
        # a) Current character begins
        # a new subsequence.
        # b) Current character is part
        # of aCount subsequences.
        # c) Current character is not
        # part of aCount subsequences.
        if (s[i] == 'a'):
            aCount = (1 + 2 * aCount)
 
        # If current character is 'b', then
        # there are following possibilities :
        # a) Current character begins a
        # new subsequence of b's with
        # aCount subsequences.
        # b) Current character is part
        # of bCount subsequences.
        # c) Current character is not
        # part of bCount subsequences.
        elif (s[i] == 'b'):
            bCount = (aCount + 2 * bCount)
 
        # If current character is 'c', then
        # there are following possibilities :
        # a) Current character begins a
        # new subsequence of c's with
        # bCount subsequences.
        # b) Current character is part
        # of cCount subsequences.
        # c) Current character is not
        # part of cCount subsequences.
        elif (s[i] == 'c'):
            cCount = (bCount + 2 * cCount)
 
    return cCount
 
# Driver code
if __name__ == "__main__":
    s = "abbc"
    print(countSubsequences(s))
 
# This code is contributed
# by ChitraNayal


C#
// C# program to count subsequences
// of the form a^i b^j c^k
using System;
 
public class GFG {
 
    // Returns count of subsequences
    // of the form a^i b^j c^k
    static int countSubsequences(String s)
    {
        // Initialize counts of different
        // subsequences caused by different
        // combination of 'a'
        int aCount = 0;
 
        // Initialize counts of different
        // subsequences caused by different
        // combination of 'a' and
        // different combination of 'b'
        int bCount = 0;
 
        // Initialize counts of different
        // subsequences caused by different
        // combination of 'a', 'b' and 'c'
        int cCount = 0;
 
        // Traverse all characters of given string
        for (int i = 0; i < s.Length; i++) {
 
            // If current character is 'a', then
            // there are following possibilities :
            // a) Current character begins a
            // new subsequence.
            // b) Current character is part
            // of aCount subsequences
            // c) Current character is not part
            // of aCount subsequences.
 
            if (s[i] == 'a')
                aCount = (1 + 2 * aCount);
 
            // If current character is 'b', then
            // there are following possibilities :
            // a) Current character begins a new
            // subsequence of b's with aCount
            // subsequences.
            // b) Current character is part of bCount
            // subsequences.
            // c) Current character is not part of
            // bCount subsequences.
            else if (s[i] == 'b')
                bCount = (aCount + 2 * bCount);
 
            // If current character is 'c', then
            // there are following possibilities :
            // a) Current character begins a new
            // subsequence of c's with bCount
            // subsequences.
            // b) Current character is part of cCount
            // subsequences.
            // c) Current character is not part of
            // cCount subsequences.
            else if (s[i] == 'c')
                cCount = (bCount + 2 * cCount);
        }
 
        return cCount;
    }
 
    // Driver code
    public static void Main()
    {
        String s = "abbc";
        Console.Write(countSubsequences(s));
    }
}
 
// This code is contributed by Nitin Mittal.


PHP


Javascript


输出:

3

复杂度分析:

  • 时间复杂度: O(n)。
    需要对字符串一次遍历。
  • 辅助空间: O(1)。
    不需要额外的空间。