1010. Zipper

来源:互联网 发布:20人企业网络解决方案 编辑:程序博客网 时间:2024/04/30 08:32

   看到题目时,想到了用dfs, 无奈从头开始搜时会超时,百度之后,有大神说需要从尾开始搜索,遂修改之AC

   这是dfs的代码

  

// Problem#: 1010// Submission#: 2717869// The source code is licensed under Creative Commons Attribution-NonCommercial-ShareAlike 3.0 Unported License// URI: http://creativecommons.org/licenses/by-nc-sa/3.0/// All Copyright reserved by Informatic Lab of Sun Yat-sen University#include <iostream> #include <string>#include <string.h>#include <queue>#include <vector>#include <stdio.h>#include <math.h>#include <list>#include <stack>using namespace std;int main(){    int n;        cin >> n;    int seq = 1;    while(n !=0)    {        string s1,s2;        string target;        cin >>s1>>s2>>target;        int ind1=s1.length()-1,ind2=s2.length()-1;        int k = target.length()-1;        cout<<"Data set "<<seq<<": ";        int *original = new int[target.length()];        bool *flag1 = new bool[s1.length()];        for(int i=0;i<s1.length();i++)            flag1[i] = false;        bool *flag2 = new bool[s2.length()];        for(int i=0;i<s2.length();i++)            flag2[i] = false;        stack<int> st;    //记录在哪些位置两个字符串的字母一样        while(k >=0 )        {            while( ind1 >=0  && target[k]== s1[ind1] || ind2 >=0 && target[k]==s2[ind2])            {                while(ind1 >=0 && s1[ind1] == target[k] && flag1[ind1]==false)                {                    if( ind2 >=0 && s1[ind1]==s2[ind2])                        st.push(k);                    original[k] = 1;                    if(ind2 >=0)                        flag2[ind2] = false;                    ind1--;                    k--;                }                while( ind2 >=0 && s2[ind2] == target[k] && flag2[ind2]==false)                {                    if(ind1 >= 0 && s2[ind2]==s1[ind1])                        st.push(k);                    original[k] = 2;                    if(ind1 >=0 )                        flag1[ind1] = false;                    ind2--;                    k--;                }            }            if(k >=0 )            {                if(st.empty())                {                    break;                }                else                {                    int pos = st.top();                    st.pop();                    while(k < pos)                    {                        k++;                        if(original[k] == 1)                            ind1++;                        else                            ind2++;                                        }                    if(original[k]==1)                        flag1[ind1] = true;                    else                        flag2[ind2] = true;                }            }        }        if( k  < 0)            cout<<"yes"<<endl;        else            cout<<"no"<<endl;                seq++;        n--;    }}                                 


 百度之后,发现还有可以使用dp(动态规划)的方法,参考了如下的博主的想法

http://www.cnblogs.com/sysuwhj/archive/2011/04/08/2009905.html

//设dp[i][j]为a串的前i个字符和b串的前j个字符能否组成c的i+j个字符
//dp[i][j] = (dp[i-1][j] && c[i+j] == a[i]) || (dp[i][j-1] && c[i+j] = b[j])

// Problem#: 1010// Submission#: 2718201// The source code is licensed under Creative Commons Attribution-NonCommercial-ShareAlike 3.0 Unported License// URI: http://creativecommons.org/licenses/by-nc-sa/3.0/// All Copyright reserved by Informatic Lab of Sun Yat-sen University#include <iostream> #include <string>#include <string.h>#include <queue>#include <vector>#include <stdio.h>#include <math.h>#include <list>#include <stack>using namespace std;int main(){    int n;        cin >> n;    int seq = 1;    while(n !=0)    {        string s1,s2;        string target;        cin >>s1>>s2>>target;        cout<<"Data set "<<seq<<": ";        int len1 = s1.length();        int len2 = s2.length();        bool **dp = new bool*[len1+1];        for(int i=0;i<=len1;i++)            dp[i] = new bool[len2+1];        for(int i=0;i<=len1;i++)            for(int j=0;j<=len2;j++)                dp[i][j] = false;                dp[0][0] = true;         for (int i = 0; i < len2; i++)      //关键之处1            if (s2[i] == target[i])                dp[0][i+1] = true;            else                break;             for (int i = 0; i < len1; i++)    //关键之处2            if (s1[i] == target[i])                dp[i+1][0] = true;            else                break;        if(target[0] == s1[0])            dp[1][0]  = true;        if(target[0] == s2[0])            dp[0][1] = true;        for(int i=1;i<=len1;i++)            for(int j=1;j<=len2;j++)                dp[i][j] = (dp[i-1][j] && s1[i-1]==target[i+j-1]) || (dp[i][j-1] && s2[j-1]==target[i+j-1]);        if(dp[len1][len2])            cout<<"yes"<<endl;        else            cout<<"no"<<endl;                seq++;        n--;    }}                                 










0 0
原创粉丝点击