打cf的时候遇到的问题,clairs告诉我这是POI2012 的原题。。原谅我菜没写过。。于是拐过来写这道题并且学了下string hash。
 
字符串hash基于Rabin-Karp算法,并且对于各种长度子串的匹配是常数的。具体做法看代码就明白了。然后如果单hash没发过。那就试试双hash把。如果还不行那就三hash以此类推。。一般到双hash就基本不会出错。你的hash的mod值要尽量分开和是素数就对了。
这种方法实在是神,当数据过大时才会可能出错2333很适合竞赛。
附加一个类似双hash的做法,zy大神的做法。就是一个hash还是正常的hash,另一个hash则被替代成了这两段子串的ascii总和的比较。这个做法也是很不错的。
推荐07年杨弋的论文《Hash在信息学竞赛中的一类应用》,对hash应用讲解很不错。

2803: [Poi2012]Prefixuffix

Time Limit: 10 Sec  Memory Limit: 64 MB
Submit: 434  Solved: 175
[Submit][Status][Discuss]

Description

对于两个串S1、S2,如果能够将S1的一个后缀移动到开头后变成S2,就称S1和S2循环相同。例如串ababba和串abbaab是循环相同的。
给出一个长度为n的串S,求满足下面条件的最大的L:
1. L<=n/2
2. S的L前缀和S的L后缀是循环相同的。

Input

第一行一个正整数n (n<=1,000,000)。第二行n个小写英文字母,表示串S。

Output

一个整数,表示最大的L。

Sample Input

15
ababbabababbaab

Sample Output

6

HINT

 

Source

 

 
代码其实大同小异。。hash代码长得都差不多,我双hash过得。
首先如果是循环同构,匹配的两串中一串相当于另一个串的左端部分的串被取出放到了右端。例如abcdefg和cdefgab。那么就题目给出的字符串,我们查找同构的前缀和后缀,同构的字符串就可以分为两部分,一部分就是前面说的左端换到右端的串,这两串是相同的,另一部分就是不动的串。因此我们枚举所有可能被换到右端的长度i,先检查转换串[1,i]和[i,n-i+1]是否匹配,然后计算[i+1,n-i]前后缀最长匹配长度f[i+1]。这样算出来的f[i+1]+i最大的即为答案。
而我们可以发现f[i]≤f[i+1]+2,因为[i,n-i+1]比[i+1,n-i]首尾各多了两个字符,对应最长匹配的串首和尾。自己纸上写写就知道了。
因此我们i从n/2枚举到1,得出最长的那个即为答案。
注意L≤n/2,所以你这个同构串是不能重叠的。
 #include<bits/stdc++.h>
#define clr(x) memset(x,0,sizeof(x))
#define clr_1(x) memset(x,-1,sizeof(x))
#define LL long long
//usually mod num is 1004535809 99824435 1000000007
#define pnum 233
#define INF 0x3f3f3f3f
using namespace std;
const int N=1e6+;
int f[N],power[N][],hash[N][],mod[]={,};
inline int gethash(int l,int r,int x)
{
return (hash[r][x]-(LL)hash[l-][x]*power[r-l+][x]%mod[x]+mod[x])%mod[x];
}
inline bool check(int x,int y,int len)
{
return gethash(x,x+len-,)==gethash(y,y+len-,) && gethash(x,x+len-,)==gethash(y,y+len-,);
}
int n,ans;
char s[N];
int main()
{
scanf("%d",&n);
scanf("%s",s);
power[][]=power[][]=;
hash[][]=hash[][]=;
for(int i=;i<=n;i++)
for(int j=;j<;j++)
{
power[i][j]=(LL)power[i-][j]*pnum%mod[j];
hash[i][j]=((LL)hash[i-][j]*pnum+(s[i-]-'a'))%mod[j];
}
f[n/+]=;
ans=;
for(int i=n/;i>=;i--)
{
f[i]=min(f[i+]+,n/-i+);
while(f[i] && !check(i,n-i-f[i]+,f[i])) f[i]--;
if(check(,n-i+,i-))
ans=max(f[i]+i-,ans);
}
printf("%d\n",ans);
return ;
}

bzoj 2803 [Poi2012]Prefixuffix 兼字符串hash入门的更多相关文章

  1. bzoj 2803 [POI2012]prefixuffix hsh+性质

    题目大意 bzoj 2803 对于两个串S1.S2,如果能够将S1的一个后缀移动到开头后变成S2,就称S1和S2循环相同.例如串ababba和串abbaab是循环相同的. 给出一个长度为n的串S,求满 ...

  2. BZOJ 2795: [Poi2012]A Horrible Poem( hash )

    ...字符串hash. 假如长度x是一个循环节, 那么对于任意n(x | n)也是一个循环节. 设当前询问区间[l, r]长度为len = ∏piai, 最终答案ans = ∏piai' ,我们只需枚 ...

  3. 字符串hash入门

    简单介绍一下字符串hash 相信大家对于hash都不陌生 翻译过来就是搞砸,乱搞的意思嘛 hash算法广泛应用于计算机的各类领域,像什么md5,文件效验,磁力链接 等等都会用到hash算法 在信息学奥 ...

  4. bzoj 2795 [Poi2012]A Horrible Poem hash+数论

    2795: [Poi2012]A Horrible Poem Time Limit: 50 Sec  Memory Limit: 128 MBSubmit: 640  Solved: 322[Subm ...

  5. bzoj 2795 [Poi2012]A Horrible Poem hash+线性筛

    题目大意 bzoj 2795 给出一个由小写英文字母组成的字符串S,再给出q个询问,要求回答S某个子串的最短循环节. 如果字符串B是字符串A的循环节,那么A可以由B重复若干次得到. n<=500 ...

  6. HDU 1880 字符串hash 入门题

    Problem Description 哈利波特在魔法学校的必修课之一就是学习魔咒.据说魔法世界有100000种不同的魔咒,哈利很难全部记住,但是为了对抗强敌,他必须在危急时刻能够调用任何一个需要的魔 ...

  7. [BZOJ2803][Poi2012]Prefixuffix

    2803: [Poi2012]Prefixuffix Time Limit: 10 Sec  Memory Limit: 64 MBSubmit: 219  Solved: 95[Submit][St ...

  8. [BZOJ 4820] [SDOI2017] 硬币游戏(高斯消元+概率论+字符串hash)

    [BZOJ 4820] [SDOI2017] 硬币游戏(高斯消元+概率论+字符串hash) 题面 扔很多次硬币后,用H表示正面朝上,用T表示反面朝上,会得到一个硬币序列.比如HTT表示第一次正面朝上, ...

  9. 字符串Hash || BZOJ 3555: [Ctsc2014]企鹅QQ || P4503 [CTSC2014]企鹅QQ

    题面:[CTSC2014]企鹅QQ 题解:无 代码: #include<iostream> #include<cstring> #include<cstdio> # ...

随机推荐

  1. 【BZOJ】1585: [Usaco2009 Mar]Earthquake Damage 2 地震伤害

    [题意]给定无向图,现在可能有一些点已经被删除,只给出信息是c个点未被删除且不能到达结点1,求最少的删除点个数. [算法]最小割 [题解]本题和1的区别是:1求的是最少的不能到达1的结点数,那么就把损 ...

  2. 数据分析之CE找数据大法

    一.基本介绍 CE的全称为Cheat Engine,是一款内存修改编辑工具,其官网是http://www.cheatengine.org,可以在其官网下载到最新的CE工具,目前最新版本是Cheat E ...

  3. JVM在遇到OOM(OutOfMemoryError)时生成Dump文件

    方法一: 命令:jmap -dump:format=b,file=heap.bin file:保存路径及文件名pid:进程编号(windows通过任务管理器查看,linux通过ps aux查看) du ...

  4. Linux-进程间通信(N): 各种IPC的使用场景

    1. 管道:只能用于具有亲缘关系的进行通信,使用面相对较窄,实际开发中较少使用: 2. FIFO(命名管道):可以用于任意进程间的通信,对于大块数据的传输效率较高,可应用于单进程大量数据传递,和多个进 ...

  5. 安全测试===sqlmap

    本文转自:https://www.secpulse.com/archives/4213.html   鉴于很多新手对sqlmap的用法不是很熟悉 很多常用sqlmap的也不一定完全会用sqlmap 特 ...

  6. selenium.webdriver.common.keys 模块中常用的变量

    表11-5 selenium.webdriver.common.keys 模块中常用的变量属性 含义Keys.DOWN, Keys.UP, Keys.LEFT,Keys.RIGHT 键盘箭头键Keys ...

  7. HDU 6188 Duizi and Shunzi 贪心

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6188 题意:给了n个数,然后现在问我们最多构成多少个对子和顺子,其中对子是2个相同的牌,顺子是3个连续 ...

  8. aspxgridview export导出数据,把true显示成‘是’

    项目原因,数据库中的数据是‘true’还有‘false’,但是在页面上要显示为‘是否’,导出来的时候也是要显示成‘是否’ 要在web页面当中显示成‘是否’,只要在gridview的CustomColu ...

  9. shell常见操作整理(更新)

    查看文件第20到30行的内容 法一:[root@oldboy ~]# seq 100 > ett.txt [root@oldboy ~]# head -30 ett.txt | tail -11 ...

  10. php设计模式三-----建造者模式

    1.简介 意图:将一个复杂的构建与其表示相分离,使得同样的构建过程可以创建不同的表示. 主要解决:主要解决在软件系统中,有时候面临着"一个复杂对象"的创建工作,其通常由各个部分的子 ...