zoukankan      html  css  js  c++  java
  • hdu 4300 Clairewd’s message (扩展KMP)

    这道题问的就是将1个串如何变为stringA+stringB的形式,使得stringA是stringB经过映射得到相同的串。映射那步其实没有什么 价值,假设str为原串s经过映射后得到的串,我们可以以str为模式串,以s为原串做一次扩展KMP,得到extend数组,extend[i]表示原 串以第i开始与模式串的前缀的最长匹配。经过O(n)的枚举,我们可以得到,若extend[i]+i=len且i>=extend[i]时,表示 stringB即为该点之前的串,stringA即为该点之前的str串,最后输出即可。


    #include<stdio.h> #include<string.h> #include<map> #define maxn 200000 using namespace std; map<char,char>map1; int max(int x,int y) { return x>y?x:y; } char s[maxn],tab[maxn],c[maxn]; int next[maxn],extend[maxn]; void EKMP(char s[],char t[])//s[]为主串,t[]为模版串 { int i,j,p,l; int len=strlen(t); int len1=strlen(s); memset(next,0,sizeof(next)); memset(extend,0,sizeof(extend)); next[0]=len; j=0; while(1+j<len&&t[j]==t[1+j])j++; next[1]=j; int a=1; for(i=2;i<len;i++) { p=next[a]+a-1; l=next[i-a]; if(i+l<p+1)next[i]=l; else { j=max(0,p-i+1); while(i+j<len&&t[i+j]==t[0+j])j++; next[i]=j; a=i; } } j=0; while(j<len1&&j<len&&s[j]==t[j])j++; extend[0]=j; a=0; for(i=1;i<len1;i++) { p=extend[a]+a-1; l=next[i-a]; if(l+i<p+1)extend[i]=next[i-a]; else { j=max(0,p-i+1); while(i+j<len1&&j<len&&s[i+j]==t[j])j++; extend[i]=j; a=i; } } } int main() { int i,j; int t; scanf("%d",&t); while(t--) { scanf("%s%s",tab,s); int len=strlen(tab); int len1=strlen(s); for(i=0;i<len;i++) { map1[tab[i]]='a'+i; } for(i=0;i<len1;i++) { c[i]=map1[s[i]]; } c[i]='\0'; EKMP(s,c); for(i=0;i<len1;i++) { if(i+extend[i]>=len1&&i>=extend[i]) { break; } } for(j=0;j<i;j++)printf("%c",s[j]); for(j=0;j<i;j++)printf("%c",map1[s[j]]); printf("\n"); } }
  • 相关阅读:
    如何删除Windows的服务
    在使用ORACLE时常用到的命令和脚本
    windows 查看端口使用情况
    jQuery获取及设置单选框,多选框,文本框内容
    disabled="disabled" readonly="readonly" type="hidden"提交表单的区别
    @Column标记持久化详细说明
    jQuery核心及其工具
    Hibernate JPA注解说明
    php要点
    jQuery中的动画与效果
  • 原文地址:https://www.cnblogs.com/acSzz/p/2601991.html
Copyright © 2011-2022 走看看