Aru*_*run 6 algorithm dynamic-programming
我正在练习面试并在网站上遇到这个问题:
字符串的神奇子序列
S是按顺序S包含所有五个元音的子序列.找到字符串最大的魔法子序列的长度S.例如,如果
S = aeeiooua,然后aeiou和aeeioou是神奇的子序列,但aeio并aeeioua不是.
我是动态编程的初学者,我发现很难想出一个递归的公式.
我用一种迭代的方法而不是递归的方法。我开始构建类似于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;
}
Run Code Online (Sandbox Code Playgroud)
小智 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;
}
Run Code Online (Sandbox Code Playgroud)