POJ 2217:Secretary(后缀数组)

Posted QTY_YTQ的博客

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了POJ 2217:Secretary(后缀数组)相关的知识,希望对你有一定的参考价值。

题目大意:求两个字符串的公共子串。

分析:

  模板题,将两个字符串接起来用不会出现的字符分割,然后求分属两个字符串的相邻后缀lcp的最大值即可。

代码:

program work;
type
  arr=array[0..20001]of longint;
var
  sa,rank,b,tmp,lcp:arr;
  n,i,m,l,u,ans,t:longint;
  s,s1,s2:ansistring;
  ch:char;
function compare(i,j,k:longint):longint;
var ri,rj:longint;
begin
  if rank[i]<>rank[j] then exit(ord(rank[i]<rank[j]))
   else
     begin
       if i+k<=n then ri:=rank[i+k] else ri:=-1;
       if j+k<=n then rj:=rank[j+k] else rj:=-1;
       exit(ord(ri<rj));
     end;
end;
procedure qsort(l,h,k:longint; var a:arr);
var i,j,t,m:longint;
begin i:=l; j:=h;
  m:=a[(i+j) div 2];
 repeat
while compare(a[i],m,k)=1 do inc(i);
while compare(m,a[j],k)=1 do dec(j);
if i<=j then
 begin   t:=a[i]; a[i]:=a[j]; a[j]:=t;
inc(i); dec(j);  end;  until i>j;
 if i<h then qsort(i,h,k,a); if j>l then qsort(l,j,k,a);  end;
procedure work_sa(s:ansistring; var sa:arr);
var k,i:longint;
begin
  for i:=1 to n do begin sa[i]:=i;  rank[i]:=ord(s[i]); end;
  k:=1;
  while k<=n do
   begin
     qsort(1,n,k,sa);
     tmp[sa[1]]:=1;
     for i:=2 to n do
       tmp[sa[i]]:=tmp[sa[i-1]]+compare(sa[i-1],sa[i],k);
     rank:=tmp;
     k:=k*2;
   end;
end;
function max(x,y:longint):longint;
begin
   if x>y then max:=x else max:=y;
end;
procedure work_lcp(s:ansistring;var sa,lcp:arr);
var i,j,h:longint;
begin
  for i:=1 to n do rank[sa[i]]:=i;
  h:=0; lcp[1]:=0; sa[0]:=0;rank[0]:=0;
  for i:=1 to n do
   begin
     j:=sa[rank[i]-1];
     if h>0 then dec(h);
     while (i+h<=n)and(j+h<=n) do
      begin
        if s[i+h]<>s[j+h] then break; inc(h);
      end;
     lcp[rank[i]-1]:=h;
   end;
end;
begin
  readln(u);
  for l:=1 to u do
   begin
     readln(s1); readln(s2);
     s:=s1+\'@\'+s2;
     t:=length(s1);
     n:=length(s); work_sa(s,sa);
     work_lcp(s,sa,lcp); ans:=0;
    for i:=1 to n-1 do begin
      if ((sa[i]<=t)and(sa[i+1]>=t+2))or((sa[i+1]<=t)and(sa[i]>=t+2)) then ans:=max(ans,lcp[i]);
    end;
     writeln(\'Nejdelsi spolecny retezec ma delku \',ans,\'.\');
  end;
end.
View Code

 

以上是关于POJ 2217:Secretary(后缀数组)的主要内容,如果未能解决你的问题,请参考以下文章

POJ2774 后缀自动机&后缀数组

POJ3080 POJ3450Corporate Identity(广义后缀自动机||后缀数组||KMP)

poj3729后缀数组

POJ 3415 后缀数组

poj 2406 Power Strings 后缀数组解法

POJ3261(后缀数组+2分枚举)