题目链接:
http://acm.hdu.edu.cn/showproblem.php?pid=5414
解题思路:
官方题解:
Let us assume that ss can be converted into tt.
Obviously, ss must be subsequence of tt. We can check this in linear time.
And, we also consider state of the first character.
If the first kk characters of tt are equal to cc, the first kk characters of ss must be also equal to cc.
It can be easily proved that s can be converted into t when the above two conditions are satisfied.
Time complexity:O(|s|+|t|)O(∣s∣+∣t∣)
题目大意:
输入两个字符串s和t,你可以选择字符串s中的任意一个字母c,在这个字母的后面加任意一个不是x的字母。最后使s变成t。如果能变成t输出Yes,否则
输出No。
算法思想:
1、t开头的几个相同的字符的字母必须能和s对应。
2、字符串t包含字符串s,也就是说s出现的字母在t里必须都有。否则aab、aaaaa这样的就不行。你无论如何也添加不出来。
唯一比较难想的是诸如ale如果添加到apple,似乎需要往a后面加2个p才能得到,但其实可以通过先加一个p,然后再向a后加1个p,就可以成功避开题
目c!=d的限制.。。
其实仔细一分析,成功转化只包含两种情况。
第一种因为要求插入的新字符和它前面的字符c不同,如果t前面中有x个连续的c,那么在s中也必须有x个连续的c;
第二种是s必须是t的一个不连续子串。
AC代码:
#include <iostream> #include <cstdio> #include <cstring> using namespace std; const int N = 100005; char s[N],t[N]; int solve(){ int i,j; int l1 = strlen(s); int l2 = strlen(t); for(i = 1; i < l2; i++) if(t[i] != t[0]) break;//找到t串的第一个不连续的位置 for(j = 0; j < i; j++)//看s的前i个子串是否连续 if(s[j] != t[0]) return 0; for(; j<l1;){ for(; i<l2; i++){//找到下一个和s相等的地方 if(t[i] == s[j]) break; } if(i == l2) return 0;//如果t找完了还没跳出证明s不是t的子串 i++; j++; } return 1; } int main(){ int T; scanf("%d",&T); while(T--){ scanf("%s%s",s,t); if(solve()) printf("Yes\n"); else printf("No\n"); } return 0; }