Cod sursa(job #311789)

Utilizator tibiletsKoos Tiberiu Iosif tibilets Data 4 mai 2009 09:57:47
Problema Flux maxim de cost minim Scor 70
Compilator cpp Status done
Runda Arhiva educationala Marime 2.25 kb
#include<fstream.h>
struct nod
{short inf;nod* adr;}*g[351];//listele de adiacenta ale grafului
void push(nod *&l,int x){nod *p=new nod;p->inf=x;p->adr=l;l=p;}
int min(int x,int y){return x<y?x:y;}
short n,m,s,d,heap[351],poz[351],l,t[351],cap[351][351];//poz - pozitia in heap, l - dimensiunea heap-ului
int dr,sc,dist[351],fl[351][351],cost[351][351];//sc - suma costurilor pe drumul de ameliorare, t - vector de tati pentru pastrarea drumului
void bf()
{int i=1,j,ok=1;
 for(;i<=n;++i)dist[i]=4444444;
 dist[s]=0;
 for (i=1;i<=n&&ok;++i)
 {ok=0;
  for(j=1;j<=n;++j)
   for(nod *p=g[j];p;p=p->adr)
	if(cap[j][p->inf]>0&&dist[j]+cost[j][p->inf]<dist[p->inf])
	{ok=1;
	 dist[p->inf]=dist[j]+cost[j][p->inf];}}
 sc=dist[d];}
void swap(short &x,short &y){short a=x;x=y;y=a;}
void perc(short k)
{while(k/2>1&&dist[heap[k]]<dist[heap[k/2]])
 {swap(heap[k],heap[k/2]);
  poz[heap[k]]=k;k/=2;
  poz[heap[k]]=k;}}
void sift(short k)
{short f;
 do  {f=k;
	  if(2*f<=l&&dist[heap[k]]>dist[heap[f*2]]) k=2*f;
	  if(2*f+1<=l&&dist[heap[k]]>dist[heap[f*2+1]]) k=2*f+1;
	  swap(heap[k],heap[f]);
	  poz[heap[k]]=k;
	  poz[heap[f]]=f;}
	  while(k!=f);}
int djk()
{int i=1,j;
 for(;i<=n;++i)
  for(nod *p=g[i];p;p=p->adr) 
   if(dist[i]!=4444444&&dist[p->inf]!=4444444) cost[i][p->inf]+=dist[i]-dist[p->inf];
 for(i=1;i<=n;++i)
 {dist[i]=4444444;t[i]=-1;
  heap[i]=i;poz[i]=i;}
 dist[s]=0;l=n;
 heap[s]=1;heap[1]=s;
 poz[s]=1;poz[1]=s;
 while(l>1&&dist[heap[1]]!=4444444)
 {for(nod *p=g[heap[1]];p;p=p->adr)
  {j=p->inf;
   if(cap[heap[1]][j]-fl[heap[1]][j]>0&&dist[heap[1]]+cost[heap[1]][j]<dist[j])
   {dist[j]=dist[heap[1]]+cost[heap[1]][j];
	t[j]=heap[1];
	perc(poz[j]);}}
  heap[1]=heap[l];--l;
  poz[heap[1]]=1;
  if(l>1) sift(1);}
 if(dist[d]!=4444444) 
 {j=4444444;dr=1;
  for(i=d;i!=s;i=t[i]) 
   j=min(j,cap[t[i]][i]-fl[t[i]][i]);
  for(i=d;i!=s;i=t[i]) 
   {fl[t[i]][i]+=j;
	fl[i][t[i]]-=j;}
  sc+=dist[d];
  return j * sc;}
 return 0;}
int main()
{ifstream f("fmcm.in");
ofstream h("fmcm.out");
short i,x,y,c,z;int flx=0;
f>>n>>m>>s>>d;
for (i = 1; i <= m; i++)
{f>>x>>y>>c>>z;
 push(g[y],x);push(g[x],y);
 cap[x][y]=c;
 cost[x][y]=z;cost[y][x]=-z;}
bf();//Bellman-Ford
do	{dr=0;
	 flx+=djk();}
while(dr);
h<<flx;
return 0;
}