Cod sursa(job #82622)

Utilizator gurneySachelarie Bogdan gurney Data 7 septembrie 2007 21:15:55
Problema Critice Scor 90
Compilator fpc Status done
Runda Arhiva de probleme Marime 3.93 kb
program critice;
  const
    fin='critice.in';
    fout='critice.out';
    nmax=1010;
    mmax=20020;
    inf=maxlongint shr 1;
type
  int=array[1..nmax] of integer;
  lint=array[1..nmax] of longint;
  tlint=^lint;
  tinteger=^int;
  mint=array[1..mmax] of integer;
  mlint=array[1..mmax] of longint;
  mtlint=^mlint;
  mtinteger=^mint;
var
  target,prev,start:mint;
  capa,flow:mlint;
  last,pred,q:tinteger;
  used:array[1..nmax] of boolean;
  delta:tlint;
  pop,push,m,ii,cur,i,j,k,n,x,y,c,nedge:longint;
  tflow:longint;
  critic:array[1..nmax] of boolean;
  num:longint;
  label 10,20;

function min(x,y:longint):longint;
  begin
    if x<y then
      min:=x
    else
      min:=y;
  end;

procedure insert(x,y,c:longint);
  begin
    inc(nedge);
    start[nedge]:=x;target[nedge]:=y;
    capa[nedge]:=c;flow[nedge]:=0;
    prev[nedge]:=last^[x];
    last^[x]:=nedge;
    inc(nedge);
    start[nedge]:=y;target[nedge]:=x;
    capa[nedge]:=c;flow[nedge]:=0;
    prev[nedge]:=last^[y];
    last^[y]:=nedge;
  end;

function op(n:integer):integer;
  begin
    if n and 1=1 then
      op:=n+1
    else
      op:=n-1;
  end;

begin
  new(last);new(pred);new(q);new(delta);
  assign(input,fin);
    reset(input);
    readln(n,m);
    nedge:=0;
    for i:=1 to m do
      begin
        readln(x,y,c);
        insert(x,y,c);
      end;
  close(input);
  assign(output,fout);
    rewrite(output);
    tflow:=0;
    while true do
      begin
        pop:=1;push:=2;
        q^[1]:=1;
        fillchar(used,sizeof(used),false);
        delta^[1]:=inf;
        used[1]:=true;
        cur:=1;
        while pop<push do
          begin
            x:=last^[q^[pop]];
            while x>0 do
              begin
                if (abs(flow[x])<capa[x]) then
                  if (not(used[target[x]])) then
                    begin
                      used[target[x]]:=true;
                      q^[push]:=target[x];
                      inc(push);
                      pred^[target[x]]:=x;
                      delta^[target[x]]:=min(delta^[start[x]],capa[x]-flow[x]);
                      if used[n] then
                        goto 10;
                    end;
                x:=prev[x];
              end;
            inc(pop);
          end;
            if not(used[n]) then
              goto 20;
            10:cur:=n;
            x:=delta^[n];
            inc(tflow,delta^[n]);
            repeat
              x:=pred^[cur];
              inc(flow[x],delta^[n]);
              dec(flow[op(x)],delta^[n]);
              cur:=start[x];
            until cur=1;
      end;
    20:fillchar(used,sizeof(used),false);
    q^[1]:=1;pop:=1;push:=2;used[1]:=true;
    critic[1]:=true;
    while pop<push do
      begin
        cur:=q^[pop];
        inc(pop);
        x:=last^[cur];
        while x>0 do
          begin
            if (abs(flow[x])<capa[x]) and (not(used[target[x]])) then
              begin
                used[target[x]]:=true;
                q^[push]:=target[x];
                inc(push);
                critic[target[x]]:=true;
              end;
            x:=prev[x];
          end;
      end;
    fillchar(used,sizeof(used),false);
    q^[1]:=n;pop:=1;push:=2;used[n]:=true;
    while pop<push do
      begin
        cur:=q^[pop];
        inc(pop);
        x:=last^[cur];
        while x>0 do
          begin
            if (abs(flow[x])<capa[x]) and (not(used[target[x]])) then
              begin
                used[target[x]]:=true;
                q^[push]:=target[x];
                inc(push);
              end;
            x:=prev[x];
          end;
      end;
    num:=0;
    for i:=1 to nedge do
      if (critic[start[i]]) and (used[target[i]]) then
        inc(num);
    writeln(num);
    for i:=1 to nedge do
      if (critic[start[i]]) and (used[target[i]]) then
        writeln((i+1)shr 1);
  close(output);
end.