Cod sursa(job #102261)

Utilizator johnyJohny Deep johny Data 14 noiembrie 2007 10:17:04
Problema Atac Scor 0
Compilator fpc Status done
Runda Arhiva de probleme Marime 3.5 kb
const nmax=32000;
type list=^elem;
     elem=record
          nod,cost:longint;
          next:list;
          end;
var lca:array[1..8*nmax] of longint;
    l:array[1..nmax] of list;
    cost,par:array[1..nmax,0..20] of longint;
    lst:array[1..2*nmax] of longint;
    poz:array[1..nmax] of longint;
    niv:array[1..nmax] of longint;
    a,b,c,d,x,y,xp,yp,z:longint;
    n,m,f1,f2:longint;
    i,pl,p:longint;
    pp:list;
    f:text;

Function ct(x,l:longint):longint;
var i,bm,rez,lu,nod:longint;
begin
i:=0;
bm:=1;
while bm<l+1 do
      begin
      inc(i);
      bm:=bm shl 1;
      end;
dec(i);
bm:=bm shr 1;
rez:=maxlongint;
lu:=l;
nod:=x;
while lu>0 do
      begin
      if cost[nod,i]<rez
      then rez:=cost[nod,i];
      lu:=lu-bm;
      if lu=0
      then begin
           ct:=rez;
           exit;
           end;
      nod:=par[nod,i];
      while bm and lu=0 do
            begin
            dec(i);
            bm:=bm shr 1;
            end;
      end;
end;

Function min(nod,st,dr,a,b:longint):longint;
var m:longint;
    rez,q:longint;
begin
if (st<=a) and (b<=dr)
then min:=lca[nod]
else begin
     m:=(st+dr) shr 1;
     rez:=maxlongint;
     if (a<m+1)
     then begin
          q:=min(nod shl 1,st,m,a,b);
          if q<rez
          then rez:=q;
          end;
     if (b>m)
     then begin
          q:=min((nod shl 1)+1,m+1,dr,a,b);
          if q<rez
          then rez:=q;
          end;
      min:=rez;
     end;
end;

Procedure df(nod,n:longint);
var pp:list;
    i:longint;
begin
i:=0;
while par[nod,i]>0 do
      begin
      par[nod,i+1]:=par[par[nod,i],i];
      if cost[nod,i]<cost[par[nod,i],i]
      then cost[nod,i+1]:=cost[nod,i]
      else cost[nod,i+1]:=cost[par[nod,i],i];
      inc(i);
      end;
pp:=l[nod];
niv[nod]:=n+1;
while pp<>nil do
      begin
      inc(pl);
      lst[pl]:=nod;
      if poz[nod]=0
      then poz[nod]:=pl;
      df(pp^.nod,n+1);
      pp:=pp^.next;
      end;
inc(pl);
lst[pl]:=nod;
if poz[nod]=0
then poz[nod]:=pl;
end;

Function cf(x,y:longint):longint;
var p,h1,h2,d1,d2:longint;
begin
if x=y
then begin
     cf:=0;
     exit;
     end;
h1:=poz[x];
h2:=poz[y];
if h1>h2
then begin
     p:=h1;
     h1:=h2;
     h2:=p;
     end;
p:=min(1,1,pl,h1,h2);
if (niv[x]<>p) and (niv[y]<>p)
then begin
     d1:=ct(x,niv[x]-p);
     d2:=ct(y,niv[y]-p);
     if d1<d2
     then cf:=d1
     else cf:=d2;
     end
else begin
     if niv[x]=p
     then cf:=ct(y,niv[y]-p)
     else cf:=ct(x,niv[x]-p);
     end;
end;

Procedure add(nod,st,dr,k,niv:longint);
var m:longint;
begin
if (lca[nod]=0) or (lca[nod]>niv)
then lca[nod]:=niv;
if st=dr
then exit;
m:=(st+dr) shr 1;
if k<m+1
then add(nod shl 1,st,m,k,niv);
if k>m
then add((nod shl 1)+1,m+1,dr,k,niv);
end;

begin
assign(f,'atac.in');
reset(f);
readln(f,n,m,p);
for i:=2 to n do
    begin
    readln(f,f1,f2);
    cost[i,0]:=f2;
    par[i,0]:=f1;
    new(pp);
    pp^.nod:=i;
    pp^.cost:=f2;
    pp^.next:=l[f1];
    l[f1]:=pp;
    end;
readln(f,x,y,a,b,c,d);
close(f);
df(1,0);
for i:=1 to pl do
    add(1,1,pl,i,niv[lst[i]]);
for i:=1 to m-p do
    begin
    z:=cf(x,y);
    xp:=(((x*a)+(y*b)) mod n)+1;
    yp:=(((y*c)+(z*d)) mod n)+1;
    x:=xp;
    y:=yp;
    end;
assign(f,'atac.out');
rewrite(f);
for i:=1 to p do
    begin
    z:=cf(x,y);
    xp:=(((x*a)+(y*b)) mod n)+1;
    yp:=(((y*c)+(z*d)) mod n)+1;
    x:=xp;
    y:=yp;
    writeln(f,z);
    end;
close(f);
end.