这一题是AC自动机简单题
本因为非常简单的题目,却因为HDU的奇怪编译器导致PASCAL很难AC
对于所有用pascal的同学!
你们可以看一下你们的程序
1 不能用ansistring 要用array of char存储 注意 length(s) 当s是字符数组是 s的大小是你定义的大小 要注意 而且他的第一位是你定义的第一位 你可以s:array[1..10000] of char这样定义 并且当s[x]=‘’(空 不是空格)就break
2内存会MLE 这一点是因为HDU的内存不够你开50w的trie树 但是HDU的内存计算方式很有趣 不要用fillchar清理数组 一开始只要清理必须为0的数组 然后每次做完了 就把本次用到的空间清0(手动for循环清0)这样就不会MLE了 开30w的trie就可以AC了
3网上说字符串后面会有空格 这个我不确定 如果你还没有AC可以加一下判断 就把空格去掉
4这题求每个小的串是否出现过例如:
3
a
a
a
a
答案是3
这点要记住
如果还不能AC那应该就是你自己的程序问题了
网上的AC自动机教程很多
我下面贴我的pas 代码
我不习惯加注释
如果看不懂 可以google hdu 2222在第2 3页有一个pascal的题解 那个神犇的代码有注释
Run ID | Submit Time | Judge Status | Pro.ID | Exe.Time | Exe.Memory | Code Len. | Language | Author |
8502121 | 2013-06-26 15:29:15 | Accepted | 2222 | 312MS | 29872K | 2425 B | Pascal | wylissb |
code:
var
v:array[0..300005] of boolean;
w,q,next,g,fa:array[0..300005] of longint;
f:array[0..300005,1..26] of longint;
j,tt,n,t1,h,t,i,l,tot,ans,x,y:longint;
s:array[0..1000] of char;str:array[0..1000005] of char;
procedure build(k,t:longint);
var
tt:longint;
begin
if t>l then
begin
w[k]:=w[k]+1;
exit;
end;
tt:=ord(s[t])-96;
if f[k,tt]=0 then
begin
tot:=tot+1;
g[tot]:=tt;
fa[tot]:=k;
f[k,tt]:=tot;
build(tot,t+1);
end
else
build(f[k,tt],t+1);
end;
procedure work(x:longint);
begin
if x=1 then exit;
ans:=ans+w[x];
w[x]:=0;
if v[x] then work(next[x]);
v[x]:=false;
end;
begin
readln(t1);
fillchar(v,sizeof(v),true);
fillchar(next,sizeof(next),0);
for t1:=1 to t1 do
begin
tot:=1;ans:=0;
readln(n);
for i:=1 to n do
begin
readln(str);
l:=length(str);
for j:=0 to l do
if (97<=ord(str[j])) and (ord(str[j])<=ord('z')) then s[j+1]:=str[j] else break;
l:=j;
build(1,1);
end;
h:=1;t:=1;
q[h]:=1;fa[1]:=1;
while h<=t do
begin
x:=q[h];y:=fa[x];
while y<>1 do
begin
y:=next[y];
if f[y,g[x]]<>0 then
begin
next[x]:=f[y,g[x]];
break;
end;
end;
if next[x]=0 then next[x]:=1;
for i:=1 to 26 do
if f[x,i]<>0 then
begin
t:=t+1;
q[t]:=f[x,i];
end;
h:=h+1;
end;
readln(str);
l:=length(str);
x:=1;
for i:=0 to l do
begin
if (str[i]=' ') or (str[i]='') then break;
tt:=ord(str[i])-96;
while (f[x,tt]=0) and (x<>1) do
x:=next[x];
if f[x,tt]<>0 then
begin
x:=f[x,tt];
ans:=ans+w[x];w[x]:=0;
if v[x] then work(x);
v[x]:=false;
end;
end;
writeln(ans);
for i:=1 to tot do
begin
w[i]:=0;fa[i]:=0;g[i]:=0;next[i]:=0;
v[i]:=true;
for j:=1 to 26 do
f[i,j]:=0;
end;
end;
end.