输入三个字符串s1、s2和s3,判断第三个字符串s3是否由前两个字符串s1和s2交错而成,即不改变s1和s2中各个字符原有的相对顺序,例如当s1 = “aabcc”,s2 = “dbbca”,s3 = “aadbbcbcac”时,则输出true,但如果s3=“accabdbbca”,则输出false。
分析
按照原文的分析,考察的是动态规划的知识。
不过原文里的代码,我看着有点奇怪,感觉是错的。
我试了试,dp矩阵打印出来确实是错的。
下面是我改写的,dp矩阵的第0行,还有第0列,都是单独拿出来初始化的,dp[ii][0] = true 含义是string s1[0...ii-1] 在string s2为空的情况下,和string s3[0...ii-1]相等;
同理可得dp[0][jj]的含义。
#include
#include
using namespace std;
bool isInterleave(string &s1, string &s2, string &s3)
{
int len1 = s1.length();
int len2 = s2.length();
int len3 = s3.length();
if (len1 + len2 != len3)
{
return false;
}
if (0 == len1)
{
return (s2 == s3) ? true : false;
}
if (0 == len2)
{
return (s1 == s3) ? true : false;
}
// allocating memory to store middle values
// we need a bias to get started
bool ** dp = new bool*[len1+1];
for (int ii = 0; ii < len1+1; ++ii)
{
dp[ii] = new bool [len2+1];
}
// dp[ii][jj]== true means that
// s1[0...ii-1] and s2[0...jj-1] forming s3[0...(ii+jj-1)] is true
// dp[0][0] means two null string form a null string, which is true
dp[0][0] = true;
for (int ii = 1; ii < len1+1; ++ii)
{
dp[ii][0] = (s1.substr(0,ii) == s3.substr(0,ii)) ? true : false;
}
for (int jj = 1; jj < len2+1; ++jj)
{
dp[0][jj] = (s2.substr(0,jj) == s3.substr(0,jj)) ? true : false;
}
for (int ii = 1; ii < len1+1; ++ii)
{
for (int jj = 1; jj < len2+1; ++jj)
{
if ( (dp[ii-1][jj] && s1[ii - 1] == s3[ii+jj-1]) ||
(dp[ii][jj-1] && s2[jj - 1] == s3[ii+jj-1]) )
{
dp[ii][jj] = true;
}else
{
dp[ii][jj] = false;
}
}
}
// for (int ii = 0; ii < len1+1; ++ii)
// {
// for (int jj = 0; jj < len2+1; ++jj)
// {
// //check char s3[ii+jj-1]
// if (dp[ii][jj] ||
// ((ii - 1 > 0) && dp[ii-1][jj] && s1[ii - 1] == s3[ii+jj-1]) ||
// ((jj - 1 > 0) && dp[ii][jj-1] && s2[jj - 1] == s3[ii+jj-1]) )
// {
// dp[ii][jj] = true;
// }else
// {
// dp[ii][jj] = false;
// }
// }
// }
cout << "dp matrix:" << endl;
for (int ii = 0; ii < len1 + 1; ++ii)
{
for (int jj = 0; jj < len2 + 1; ++jj)
{
cout << dp[ii][jj] << " ";
}
cout << endl;
}
bool result = dp[len1][len2];
for (int ii = 0; ii < len2+1; ++ii)
{
delete [] dp[ii];
}
delete [] dp;
return result;
}
int main()
{
string s1 = "aabcce", s2 = "dbbca";
string s3 = "aadbbcbcace";
if (isInterleave(s1, s2, s3))
{
cout << "yes" << endl;
}else
{
cout << "no" << endl;
}
}