zoukankan      html  css  js  c++  java
  • 大暴搜 字串变换

      

    65. [NOIP2002] 字串变换

    时间限制:1 s   内存限制:128 MB

    [问题描述]

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

    A1$ -> B1$

    A2$ -> B2$

    规则的含义为:在A$中的子串A1$可以变换为B1$、A2$可以变换为B2$…。

    例如:A$='abcd'  B$='xyz'

    变换规则为:‘abc’->‘xu’ ‘ud’->‘y’ ‘y’->‘yz’

    则此时,A$可以经过一系列的变换变为B$,其变换的过程为:

    ‘abcd’->‘xud’->‘xy’->‘xyz’

    共进行了三次变换,使得A$变换为B$。

    [输入]

    A$ B$

    A1$ B1$

    A2$ B2$  |->变换规则

    ... ... / 

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

    [输出]

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

    [输入样例]

    abcd xyz
    abc xu
    ud y
    y yz
    

    [输出样例]

    3 
    正解就是搜,深搜会超时,可以考虑广搜,即双向广搜,可以防止被卡数据,比如正向搜过慢,而反向搜很快的点。
    先贴一发我dfs+神剪枝+卡数据的搜
    #include<cstdio>
    #include<cstdlib>
    #include<cstring>
    #include<iostream>
    #include<algorithm>
    #include<cmath>
    #include<map>
    using namespace std;
    string A,B,a[10],b[10];
    int n=1,ans=11,cnt=0;
    map<string,int> mp;
    void dfs(string x,int len)
    {
        cnt++;
        if(cnt>=40000){printf("NO ANSWER!
    ");exit(0);}//深搜次数过多直接输出无解,卡数据。
    	if(len>10||x.size()>20||len>ans)return;
    	if(x==B){
    	    ans=min(ans,len);
    	    return;
    	}
    	string f=x;int k;
    	for(int i=1;i<=n;i++){
    		for(int j=0;j<x.size();j++)
    		{
    		   k=x.find(a[i],j);
    	       if(k<100&&k>=0)
    	       {
    		  	    int l=a[i].size();
    				x.replace(k,l,b[i]);
    		  	    if(!mp.count(x))mp[x]=len,dfs(x,len+1);
    		  	    else if(len<mp[x])dfs(x,len+1);
    		  	    x=f;
    		   }
    		}
    	}
    }
    int yjn()
    {
    	freopen("string.in","r",stdin);
    	freopen("string.out","w",stdout);
    	cin>>A>>B;
    	while(cin>>a[n])cin>>b[n++];
    	n--;
    	mp[A]=++cnt;
    	dfs(A,0);
    	if(ans==11)printf("NO ANSWER!
    ");
    	else cout<<ans;
    }
    int qty=yjn();
    int main(){;}

    再贴一发正解
     
    1. #include<iostream>
    2. #include<cstdio>
    3. #include<cstring>
    4. #include<algorithm>
    5. #include<map>
    6. #include<string>
    7. #include<queue>
    8. using namespace std;
    9. struct node
    10. {
    11. string s;int num;
    12. };
    13. queue<node>q1,q2;
    14. map<string,int>m1,m2;
    15. string changings[6][2];
    16. int cnt,ans;
    17. string become(string now,int pos,int n,string tmp)
    18. {
    19. return now.replace(pos,n,tmp);
    20. }
    21. bool dbfs()
    22. {
    23. while(!q1.empty()&&!q2.empty())
    24. {
    25. node s1=q1.front(),s2;q1.pop();
    26. int len=s1.s.size();
    27. for(int i=0;i<len;i++)
    28. for(int j=0;j<cnt;j++)
    29. {
    30. int siz=changings[j][0].size();
    31. if(i+siz-1<len&&!s1.s.compare(i,siz,changings[j][0])&&!m1.count(become(s1.s,i,siz,changings[j][1])))
    32. {
    33. s2.s=become(s1.s,i,siz,changings[j][1]);
    34. s2.num=s1.num+1;
    35. if(s2.num>10)return 0;
    36. m1[s2.s]=s2.num;q1.push(s2);
    37. if(m2.count(s2.s))
    38. {
    39. ans=s2.num+m2[s2.s];
    40. return 1;
    41. }
    42. }
    43. }
    44. s1=q2.front(),s2;q2.pop();
    45. len=s1.s.size();
    46. for(int i=0;i<len;i++)
    47. for(int j=0;j<cnt;j++)
    48. {
    49. int siz=changings[j][1].size();
    50. if(i+siz-1<len&&!s1.s.compare(i,siz,changings[j][1])&&!m2.count(become(s1.s,i,siz,changings[j][0])))
    51. {
    52. s2.s=become(s1.s,i,siz,changings[j][0]);
    53. s2.num=s1.num+1;
    54. if(s2.num>10)return 0;
    55. m2[s2.s]=s2.num;q2.push(s2);
    56. if(m1.count(s2.s))
    57. {
    58. ans=s2.num+m1[s2.s];
    59. return 1;
    60. }
    61. }
    62. }
    63. }
    64. return 0;
    65. }
    66. int haha()
    67. {
    68. freopen("string.in","r",stdin);
    69. freopen("string.out","w",stdout);
    70. node a,b;cin>>a.s>>b.s;
    71. if(a.s==b.s)
    72. {
    73. cout<<0;
    74. return 0;
    75. }
    76. a.num=b.num=0;
    77. q1.push(a);q2.push(b);
    78. while(cin>>changings[cnt][0]>>changings[cnt][1])cnt++;
    79. m1[a.s]=0;m2[b.s]=0;
    80. if(dbfs())cout<<ans;
    81. else puts("NO ANSWER!");
    82. }
    83. int sb=haha();
    84. int main(){;}
  • 相关阅读:
    Java基础-四要素之一《继承》
    Java基础-四要素之一《多态》
    Java基础-四大特性理解(抽象、封装、继承、多态)
    Java基础-父类-子类执行顺序
    Java基础--重写(Overriding,覆盖)-重载(Overloading)
    Java基础-数据类型转换
    Java基础-转义字符
    Java基础-数据类型int,short,char,long,float,double,boolean,byte
    算法-科学计算法
    Java基础-JVM堆与栈
  • 原文地址:https://www.cnblogs.com/QTY2001/p/7632729.html
Copyright © 2011-2022 走看看