• Manacher-模版题poj3974 hdu3068



    当i>mx时,就要重头开始匹配啦

    其余看代码的注释好好理解啊

    //Manacher模版题poj3974
    #include<cstdio>
    #include<cstring>
    #include<cstdlib>
    #include<iostream>
    #include<algorithm>
    using namespace std;
    #define maxn 2001000
    
    int g[maxn];char ss[maxn],s[maxn];
    //ss为原串,s是ss相邻字符间加一个奇怪字符的串
    //g[i]表示以字符s[i]为中心的最长回文长度
    int mymax(int x,int y){return (x>y)?x:y;}
    int mymin(int x,int y){return (x<y)?x:y;}
    int main()
    {
    	//freopen("a.in","r",stdin);
    	//freopen("a.out","w",stdout);
    	int len,l,ans,mx,p,Case=0;
    	while (1)
    	{
    		scanf("%s",ss+1);
    		if (strcmp(ss+1,"END")==0) break;
    		l=strlen(ss+1);
    		len=0;s[len]='|';
    		for(int i=1;i<=l;i++)
    		{
    			s[++len]=ss[i];
    			s[++len]='|';
    		}mx=0;p=0;ans=0;g[0]=1;
    		//p为当前找到的最长回文串的(中心)位置
    		//mx表示目前到达的最远位置,即最长回文串的最右端
    		for(int i=1;i<=len;i++)
    		{
    			if (mx>i) g[i]=mymin(g[2*p-i],mx-i);
    			//当mx>i时,2*p-i是i关于p的对称点,它的g值是已经算好了的,
    			//如果i+g[2*p-i]还在mx的范围里,那么g[i]=g[2*p-i]
    			//否则就是说,目前可以确定的匹配好的长度为mx-i,从mx-i开始匹配
    			else g[i]=1;//不然就从头开始匹配
    			while (i+g[i]<=len && s[i-g[i]]==s[i+g[i]]) g[i]++;//匹配ing
    			if (i+g[i]>mx) {mx=i+g[i];p=i;}//更新mx,p
    			ans=mymax(ans,g[i]);
    		}printf("Case %d: %d
    ",++Case,ans-1);//g[i]中的最大值-1即为原串的最长回文子串长度
    	}return 0;
    }


  • 相关阅读:
    初识RabbitMQ
    ThreadPoolExecutor中execute和submit的区别
    MYSQL bin_log 开启及数据恢复
    MYSQL 悲观锁和乐观锁简单介绍及实现
    linux php多版本
    easyui汉化啊!
    虚化技术的额外开销
    拍脑袋空想不可能有创新
    大规模WEB服务技术
    xunsearch bsd 10.1安装心酸路。。。
  • 原文地址:https://www.cnblogs.com/Euryale-Rose/p/6527892.html
Copyright © 2020-2023  润新知