元音的子序列

时间:2017-06-14 20:45:38

标签: algorithm dynamic-programming

我正在练习面试,并在网站上遇到了这个问题:

  

字符串S的神奇子序列是S的子序列   按顺序包含所有五个元音。找到字符串S的最大魔法子序列的长度。

     

例如,如果S = aeeiooua,则aeiouaeeioou是神奇的子序列   但aeioaeeioua不是。

我是动态编程的初学者,我发现很难想出一个递归的公式。

9 个答案:

答案 0 :(得分:4)

我用迭代方法而不是递归方法做到了。我开始构建类似于LIS(最长增加子序列)的解决方案,然后将其优化到O(n)。

#include<iostream>
#include<string>
#include<vector>
using namespace std;

string vowel = "aeiou";

int vpos(char c)
{
    for (int i = 0; i < 5; ++i)
        if (c == vowel[i])
            return i;
    return -1;
}

int magical(string s)
{
    int l = s.length();
    int previndex[5] = {-1, -1, -1, -1, -1};    // for each vowel
    vector<int> len (l, 0);
    int i = 0, maxlen = 0;

    // finding first 'a'
    while (s[i] != 'a')
    {
        ++i;
        if (i == l)
            return 0;
    }

    previndex[0] = i;       //prev index of 'a'
    len[i] = 1;

    for ( ++i; i < l; ++i)
    {
        if (vpos(s[i]) >= 0)    // a vowel
        {
            /* Need to append to longest subsequence on its left, only for this vowel (for any vowels) and 
             * its previous vowel (if it is not 'a')
                This important observation makes it O(n) -- differnet from typical LIS
            */
            if (previndex[vpos(s[i])] >= 0)
                len[i] = 1+len[previndex[vpos(s[i])]];

            previndex[vpos(s[i])] = i;

            if (s[i] != 'a')
            {
                if (previndex[vpos(s[i])-1] >= 0)
                    len[i] = max(len[i], 1+len[previndex[vpos(s[i])-1]]);
            }

            maxlen = max(maxlen, len[i]);
        }
    }
    return maxlen;
}

int main()
{
    string s = "aaejkioou";
    cout << magical(s);
    return 0;
}

答案 1 :(得分:2)

O(输入字符串长度)运行时     导入java.util。*;

Item

答案 2 :(得分:0)

#include <iostream>
#include<string>
#include<cstring>

using namespace std;
unsigned int getcount(string a, unsigned int l,unsigned int r );
int main()
{    
    std::string a("aaaaaeeeeaaaaiiioooeeeeuuuuuuiiiiiaaaaaaoo"
                 "oooeeeeiiioooouuuu");
    //std::string a("aaaaaeeeeaaaaiiioooeeeeuuuuuuiiiiiaaaaaaoooooeeeeiiioooo"); 
   //std::string a("aaaaaeeeeaaaaiiioooeeeeiiiiiaaaaaaoooooeeeeiiioooo"); //sol0
  //std::string a{"aeiou"};
  unsigned int len = a.length();
  unsigned int i=0,cnt =0,countmax =0;
  bool newstring = true;
  while(i<len)
  {
      if(a.at(i) == 'a' && newstring == true) 
      {
          newstring = false;
          cnt = getcount(a,i,len);
          if(cnt > countmax) 
          {
             countmax = cnt;
             cnt = 0;
          }
        } 
        else if(a.at(i)!='a')
        {
            newstring = true;
        }
        i++;
    }
    cout<<countmax;
    return 0;
}

unsigned int getcount(string a, unsigned int l,unsigned int r )
{
    std::string b("aeiou");
    unsigned int seq=0,cnt =0;
    unsigned int current =l;
    bool compstr = false;
    while(current<r)
    {
        if(a.at(current) == b.at(seq)) 
        {
            cnt++;
        }
        else if((seq <= (b.size()-2)) && (a.at(current) == b.at(seq+1)))
        {
            seq++; 
            cnt++;
            if (seq == 4) 
                compstr =true;
        }
        current++;
    }
    if (compstr == true) 
        return cnt;
   return 0;
}

答案 3 :(得分:0)

你可以在这里使用递归方法(这应该适用于字符串长度upto max int(可以使用容易记忆)

  iTextSharp.text.Image logo = iTextSharp.text.Image.GetInstance("/test.png");

  PdfPCell logocell = new PdfPCell(logo,true); //  **PdfPCell(Image,Boolean Fit)**

}

答案 4 :(得分:0)

这是您的问题的python代码。 它是否使用非递归方法。

从我的存储库中挑选:MagicVowels Madaditya

############################################################################
#
# Magical Subsequence of  Vowels
#       by Aditya Kothari (https://github.com/Madaditya/magivvowels)
#
#
############################################################################
import sys
import re

usage = '''
Error : Invalid no of arguments passed.
Usage :
python magicv.py string_to_check
eg: python magicv.py aaeeiiooadasduu
'''

def checkMagicVowel(input_string):
    #The Answer Variable 
    counter = 0

    #Check if all vowels exist
    if ('a' in input_string) and ('e' in input_string) and ('i' in input_string) and ('o' in input_string) and ('u' in input_string):

        vowel_string = 'aeiou'
        input_string_voweslOnly = ''

        #Keeping only vowels in the string i.e user string MINUS NON vowels
        for letter in input_string:
            if letter in 'aeiou':
                input_string_voweslOnly = input_string_voweslOnly + letter

        magic = ''
        index_on_vowel_string = 0
        current_vowel = vowel_string[index_on_vowel_string]
        #i is index on the current Character besing tested
        i = 0
        for current_char in input_string_voweslOnly:

            if current_char == current_vowel:
                counter = counter + 1
                magic = magic + current_char

            if (i < len(input_string_voweslOnly)-1):
                next_char = input_string_voweslOnly[i+1]

                if(index_on_vowel_string != 4):
                    next_vowel = vowel_string[index_on_vowel_string+1]
                else:
                    next_vowel = vowel_string[index_on_vowel_string]

                #next character should be the next new vowel only to count++
                if (current_char != next_char and next_char == next_vowel):
                        if(index_on_vowel_string != 4):
                            index_on_vowel_string = index_on_vowel_string + 1
                        current_vowel = vowel_string[index_on_vowel_string]

            i = i + 1
        #Uncomment next line to print the all magic sequences
        #print magic

        '''
        #Regex Method
        #magic = re.match('[a]+[e]+[i]+[o]+[u]+',input_string_voweslOnly)
        magic = re.match('[aeiou]+',input_string_voweslOnly)
        if magic is not None:
            ##print magic.group() 
            ##print len(magic.group())
        else:
            ##print(0)
        '''
    else:
        counter = 0
    return counter

if __name__ == "__main__":

    #checking arguments passed
    if(len(sys.argv) != 2):
        print usage
        sys.exit(0)
    input_string = sys.argv[1].lower()

    #get all possible substrings
    all_a_indices = [i for i, ltr in enumerate(input_string) if ltr == 'a']
    substrings = []
    for item in all_a_indices:
        substrings.append(input_string[item:])
    #print substrings

    #Pass each substring and find the longest magic one
    answer = []
    for each in substrings:
        answer.append(checkMagicVowel(each))
    print max(answer)

答案 5 :(得分:0)

int func( char *p)
{
    char *temp = p;
    char ae[] = {'a','e','i','o','u'};

    int size = strlen(p), i = 0;
    int chari = 0, count_aeiou=0;
    for (i=0;i<=size; i++){
        if (temp[i] == ae[chari]) {
            count_aeiou++;
        }
        else if ( temp[i] == ae[chari+1]) {
            count_aeiou++;
            chari++;
        }
    }
    if (chari == 4 ) {
        printf ("Final count : %d ", count_aeiou);
    } else {
        count_aeiou = 0;
    }
    return count_aeiou;
}

根据hackerrank挑战重新运行VOWELS计数的解决方案。

答案 6 :(得分:0)

int findsubwithcontinuousvowel(string str){
    int curr=0;
    int start=0,len=0,maxlen=0,i=0;
    for(i=0;i<str.size();i++){
        if(str[i]=='u' && (current[curr]=='u' ||  (curr+1<5 && current[curr+1]=='u'))){
           //len++;
           maxlen=max(len+1,maxlen);
        }

        if(str[i]==current[curr]){
            len++;
        }
        else if(curr+1<5 && str[i]==current[curr+1]){
            len++;
            curr++;
        }
        else{
            len=0;
            curr=0;
            if(str[i]=='a'){
                len=1;
            }
        }
    }
    return maxlen;
}

答案 7 :(得分:0)

检查元音在isInSequence中是否可用,并在processor上处理结果。

public class one {

private char[] chars = {'a','e','i','o','u'};
private int a = 0;

private boolean isInSequence(char c){
    // check if char is repeating
    if (c == chars[a]){
        return true;
    }
    // if vowels are in sequence and just passed by 'a' and so on...
    if (c == 'e' && a == 0){
        a++;
        return true;
    }
    if (c == 'i' && a == 1){
        a++;
        return true;
    }
    if (c == 'o' && a == 2){
        a++;
        return true;
    }
    if (c == 'u' && a == 3){
        a++;
        return true;
    }
    return false;
}

private char[] processor(char[] arr){
    int length = arr.length-1;
    int start = 0;
    // In case if all chars are vowels, keeping length == arr
    char array[] = new char[length];

    for (char a : arr){
        if (isInSequence(a)){
            array[start] = a;
            start++;
        }
    }
    return array;
}

public static void main(String args[]){
    char[] arr = {'m','a','e','l','x','o','i','o','u','a'};
    one o = new one();
    System.out.print(o.processor(arr));
 }
}

答案 8 :(得分:0)

#include <bits/stdc++.h>
#define ios ios::sync_with_stdio(NULL);cin.tie(NULL);cout.tie(NULL);
#define ll unsigned long long
using namespace std;

int main() {
    // your code goes here
 ios
string s;
cin>>s;
int n=s.length();
int dp[n+1][5]={0};
for(int i=1;i<=n;i++)
{
    if(s[i-1]=='a')
    {
        dp[i][0]=1+dp[i-1][0];
        dp[i][1]=dp[i-1][1];
        dp[i][2]=dp[i-1][2];
        dp[i][3]=dp[i-1][3];
        dp[i][4]=dp[i-1][4];
    }
    else if(s[i-1]=='e')
    {dp[i][0]=dp[i-1][0];
    if(dp[i-1][0]>0)
        {dp[i][1]=1+max(dp[i-1][1],dp[i-1][0]);}
        else
        dp[i-1][1]=0;
        dp[i][2]=dp[i-1][2];
        dp[i][3]=dp[i-1][3];
        dp[i][4]=dp[i-1][4];
    }
     else if(s[i-1]=='i')
    {dp[i][0]=dp[i-1][0];
    if(dp[i-1][1]>0)
        {dp[i][2]=1+max(dp[i-1][1],dp[i-1][2]);}
        else
        dp[i-1][2]=0;
        dp[i][1]=dp[i-1][1];
        dp[i][3]=dp[i-1][3];
        dp[i][4]=dp[i-1][4];
    }
    else if(s[i-1]=='o')
    {dp[i][0]=dp[i-1][0];
    if(dp[i-1][2]>0)
        {dp[i][3]=1+max(dp[i-1][3],dp[i-1][2]);}
        else
        dp[i-1][3]=0;
        dp[i][2]=dp[i-1][2];
        dp[i][1]=dp[i-1][1];
        dp[i][4]=dp[i-1][4];
    }
    else if(s[i-1]=='u')
    {dp[i][0]=dp[i-1][0];
       if(dp[i-1][3]>0)
        {dp[i][4]=1+max(dp[i-1][4],dp[i-1][3]);}
        else
        dp[i-1][4]=0;
        dp[i][1]=dp[i-1][1];
        dp[i][3]=dp[i-1][3];
        dp[i][2]=dp[i-1][2];
    }
    else
    {
        dp[i][0]=dp[i-1][0];
        dp[i][1]=dp[i-1][1];
        dp[i][2]=dp[i-1][2];
        dp[i][3]=dp[i-1][3];
        dp[i][4]=dp[i-1][4];
    }


}
cout<<dp[n][4];


return 0;
}