zoukankan      html  css  js  c++  java
  • 洛谷 P1032 字串变换

    P1032 字串变换

    题目描述

    已知有两个字串 A,BA,B 及一组字串变换的规则(至多 66 个规则):

    A_1A1 -> B_1B1

    A_2A2 -> B_2B2

    规则的含义为:在 AA 中的子串 A_1A1 可以变换为 B_1B1 , A_2A2 可以变换为 B_2B2 …。

    例如: AA =' abcdabcd ' BB =' xyzxyz '

    变换规则为:

    ‘ abcabc ’->‘ xuxu ’‘ udud ’->‘ yy ’‘ yy ’->‘ yzyz ’

    则此时, AA 可以经过一系列的变换变为 BB ,其变换的过程为:

    ‘ abcdabcd ’->‘ xudxud ’->‘ xyxy ’->‘ xyzxyz ’

    共进行了 33 次变换,使得 AA 变换为 BB 。

    输入输出格式

    输入格式:

     

    输入格式如下:

    ABB
    A_1A1 B_1B1
    A_2A2 B_2B2 |-> 变换规则

    ... ... /

    所有字符串长度的上限为 2020 。

     

    输出格式:

     

    输出至屏幕。格式如下:

    若在 1010 步(包含 1010 步)以内能将 AA 变换为 BB ,则输出最少的变换步数;否则输出"NO ANSWER!"

     

    输入输出样例

    输入样例#1: 复制
    abcd xyz
    abc xu
    ud y
    y yz
    
    输出样例#1: 复制
    3
    思路:深搜60TLE,宽搜AC.
    #include<cstdio>
    #include<cstring>
    #include<iostream>
    #include<algorithm>
    #define MAXN 100000
    using namespace std;
    int n=1,ans=0x7f7f7f7f;
    string A,B;
    int net[MAXN],vis[MAXN];
    struct nond{
        string s1,s2;
    }v[7];
    int judge(string sa,string sb){
        int len1=sa.length();
        if(len1!=sb.length())    return 0;
        else for(int i=0;i<len1;i++)
            if(sa[i]!=sb[i])    return 0;
        return 1;
    }
    void getnet(string p){
        int plen=p.length();
        net[0]=-1;
        int k=-1;
        int j=0;
        while(j<plen){
            if(k==-1||p[j]==p[k]){
                j++;k++;
                net[j]=k;
            }
            else k=net[k];
        }
    }
    int kmp(string s,string p){
        getnet(p);
        int i=0,j=0;
        int slen=s.length();
        int plen=p.length();
        while(i<slen){
            if(j==-1||s[i]==p[j]){
                i++;j++;
            }
            else    j=net[j];
            if(j==plen){
                return i-plen;
                j=0,i--;
            }
        }
        return -1;
    }
    void dfs(int tot,string s){
        if(tot==10)    return ;
        if(judge(s,B)==1){
            ans=min(ans,tot);
            return ;
        }
        for(int i=1;i<=n;i++)
            if(vis[i]<=2){
                //memset(net,0,sizeof(net));
                int l1=s.length(),l2=v[i].s1.length();
                int be=kmp(s,v[i].s1);
                if(be!=-1){
                    string s3;vis[i]++;
                    for(int j=0;j<be;j++)    s3+=s[j];
                    s3+=v[i].s2;
                    for(int j=be+l2;j<l1;j++)    s3+=s[j];
                    dfs(tot+1,s3);vis[i]--;
                }
            }
    }
    int main(){
        cin>>A>>B;
        while(cin>>v[n].s1>>v[n].s2){
            n++;
            if(n==7)    break; 
        } 
        n--;
        dfs(0,A);
        if(ans==0x7f7f7f7f)    cout<<"NO ANSWER!"<<endl;
        else cout<<ans;
    }
    60分暴力
    #include<map>
    #include<queue>
    #include<cstring>
    #include<iostream>
    #include<algorithm> 
    #define maxn 15
    using namespace std;
    struct node{
        string str;
        int step;
    };
    string a,b;
    string orginal[maxn];
    string translated[maxn];
    int n,ans;
    map<string,int>ma;
    string trans(const string &str,int i,int j){
        string ans="";
        if(i+orginal[j].length()>str.length())
            return ans;
        for (int k=0;k<orginal[j].length();k++)
            if (str[i+k]!=orginal[j][k])
                return ans;
        ans=str.substr(0,i);
        ans+=translated[j];
        ans+=str.substr(i+orginal[j].length());
        return ans;
    }
    void bfs(){
        queue<node>q;
        node s;
        s.str=a;
        s.step=0;
        q.push(s);
        while(!q.empty()){
            node u=q.front();
            q.pop();
            string temp;
            if(ma.count(u.str) == 1)    continue;
            if(u.str==b){
                ans=u.step;
                break;
            }
            ma[u.str] = 1;
            for (int i=0;i<u.str.length();i++)
                for (int j=0;j<n;j++){
                    temp=trans(u.str,i,j);
                    if(temp!=""){
                        node v;
                        v.str=temp;
                        v.step=u.step+1;
                        q.push(v);
                    }
                }
        }
        if(ans>10||ans==0)    cout<<"NO ANSWER!"<<endl;
        else    cout<<ans<<endl;
    }
    int main(){
        cin>>a>>b;
        while(cin>>orginal[n]>>translated[n])    n++;
        bfs();
        return 0;
    }
    View Code
    细雨斜风作晓寒。淡烟疏柳媚晴滩。入淮清洛渐漫漫。 雪沫乳花浮午盏,蓼茸蒿笋试春盘。人间有味是清欢。
  • 相关阅读:
    初听余杭...
    生命里走了一位花儿,同时却遇到了10年未见的老同学
    两个馒头过中秋
    周末粉红色的回忆
    jQuery图片剪裁插件 Jcrop
    上周六出去烤肉随便拍了几张
    一周学会Mootools 1.4中文教程:(7)汇总收尾
    30天学会 MooTools 教学(4): 函数和MooTools
    用Mootools寫的一个类似facebook的弹出对话框
    用Mootools获得操作索引的两种方法
  • 原文地址:https://www.cnblogs.com/cangT-Tlan/p/9341768.html
Copyright © 2011-2022 走看看