hdu4436
#include <cstring>
#include <cstdio>
#include <iostream>
#include <algorithm>
#include <vector>
#include <map>
#include <cmath>
#include <queue>
#include <string>
#include <set>
#include <stack>
using namespace std;
#define ll long long
#define eps 1e-8
#define inf 0x3f3f3f3f
#define N 100100
#define M 2002000
#define mod 2012
struct State
{
State *par,*go[11];
int len,id,pos,cnt,sum;
State(){}
State(int _len):len(_len)
{
cnt = sum = 0;
par = 0;
memset(go,0,sizeof(go));
}
}*root,*last;
State nde[N<<1];
int sz;
State* newState(int len)
{
nde[sz] = State(len);
nde[sz].id = sz;
return &nde[sz++];
}
State* newState(State* p)
{
nde[sz] = *p;
nde[sz].id = sz;
nde[sz].cnt = nde[sz].sum = 0;
return &nde[sz++];
}
void init()
{
sz = 0;
root = last = newState(0);
nde[0].pos = 0;
}
void extend(int w,int len)
{
State* p = last;
State* np = newState(p->len+1);
np->pos = len;
last = np;
while(p && p->go[w]==0)
p->go[w] = np,p = p->par;
if(p==0)
np->par = root;
else
{
State* q = p->go[w];
if(p->len+1 == q->len)
np->par = q;
else {
State* nq = newState(q);
nq->len = p->len + 1;
q->par = nq;
np->par = nq;
while(p && p->go[w]==q)
p->go[w] = nq, p = p->par;
}
}
}
void build(char *str)
{
last = root;
for(int i=0;str[i];i++)
{
if( !last->go[str[i]-'0'] || !(last->go[str[i]-'0']->len == i+1 ) )
extend(str[i]-'0',i+1);
else
last = last->go[str[i]-'0'];
}
}
char ch[N];
int topocnt[N];
State *topsam[N<<1];
int main()
{
int n;
while(scanf("%d",&n)!=EOF)
{
init();
for(int i=0;i<n;i++)
{
scanf("%s",ch);
build(ch);
}
memset(topocnt,0,sizeof(topocnt));
for(int i=0;i<sz;i++)
topocnt[nde[i].len]++;
for(int i=1;i<N;i++)
topocnt[i] += topocnt[i-1];
for(int i=0;i<sz;i++)
topsam[--topocnt[nde[i].len]] = &nde[i];
int ans = 0;
root->cnt = 1;
for(int i=0;i<sz;i++)
{
State *tmp = topsam[i];
for(int j=0;j<10;j++)
{
if( i==0 && j==0 ) continue;
if(tmp->go[j])
{
State *q = tmp->go[j];
q->cnt = (q->cnt + tmp->cnt)%mod;
q->sum = (q->sum + tmp->sum*10+tmp->cnt*j)%mod;
}
}
ans = (ans + tmp->sum)%mod;
}
printf("%d\n",ans);
}
}
code of cf244D
#include <cstring>
#include <cstdio>
#include <iostream>
#include <algorithm>
#include <vector>
#include <map>
#include <cmath>
#include <queue>
#include <string>
#include <set>
#include <stack>
using namespace std;
#define ll long long
#define eps 1e-10
#define pi acos(-1.0)
#define inf 0x3f3f3f3f
#define mod 1000000007
#define sqr(x) ((x)*(x))
#define lson (u<<1)
#define rson (u<<1|1)
#define N 100100
#define M 2002000
struct State
{
State *par,*go[26];
int val,rht;
State():par(0),val(0)
{
memset(go,0,sizeof(go));
}
};
State nde[N<<1],*cur;
int topocnt[N];
State *topsam[N<<1];
struct SuffixAc
{
State *root,*last;
char str[N];
int n;
void init(){
root = last = cur++;
n = strlen(str);
}
void extend(int w)
{
State* p = last;
State* np = cur++;
np->val = p->val + 1;
while(p && p->go[w]==0)
p->go[w] = np,p = p->par;
if(p==0)
np->par = root;
else
{
State* q = p->go[w];
if(p->val+1 == q->val)
np->par = q;
else {
State* nq = cur++;
memcpy(nq->go, q->go, sizeof q->go);
nq->val = p->val + 1;
nq->par = q->par;
q->par = nq;
np->par = nq;
while(p && p->go[w]==q)
p->go[w] = nq, p = p->par;
}
}
last = np;
}
void build()
{
init();
for(int i=0;i<n;i++)
extend(str[i]-'a');
}
void getRight()
{
int tot = cur - root;
int idx = root-nde;
memset(topocnt,0,sizeof(topocnt));
for(int i=0;i<tot;i++)
topocnt[nde[i+idx].val]++;
for(int i=1;i<=n;i++)
topocnt[i] += topocnt[i-1];
for(int i=0;i<tot;i++)
topsam[--topocnt[nde[i+idx].val]] = &nde[i+idx];
State *p = root;
for (int i = 0; i < n; i++) {
p = p->go[str[i] - 'a']; p->rht++;
}
for (int i = tot - 1; i > 0; i--){
if (topsam[i]->par) topsam[i]->par->rht += topsam[i]->rht;
}
}
}suf[2];
int main()
{
while(scanf("%s%s",suf[0].str,suf[1].str)!=EOF)
{
cur = nde;
suf[0].build();suf[0].getRight();
suf[1].build();suf[1].getRight();
int ans = inf;
for(int i=0;i<suf[0].n;i++)
{
int num1 = 0, num2 = 0;
State *p = suf[0].root;
State *q = suf[1].root;
for(int j=i;j<suf[0].n;j++)
{
if(j-i+1>=ans) break;
p = p->go[suf[0].str[j]-'a'];
q = q->go[suf[0].str[j]-'a'];
if(p) num1 = p->rht;
if(q) num2 = q->rht;
else break;
if(num1==1 && num2==1)
ans = min(ans,j-i+1);
}
}
if(ans==inf) ans = -1;
printf("%d\n",ans);
}
}