Cod sursa(job #424876)

Utilizator mihaionlyMihai Jiplea mihaionly Data 25 martie 2010 12:00:12
Problema Cuplaj maxim de cost minim Scor 70
Compilator cpp Status done
Runda Arhiva educationala Marime 1.92 kb
#include <cstdio>
#include <vector>
using namespace std;
#define inf 25000
#define nmax 610
FILE *f=fopen("cmcm.in","r");
FILE *fout=fopen("cmcm.out","w");
int n,m,e;
int M[nmax][nmax];
int Q[3000],k;
int sol[50005];
bool viz[nmax];
int drum[nmax],pre[nmax];
vector<int> Cs[nmax],G[nmax];
int C[nmax][nmax],F[nmax][nmax];
void read()
 {
 int i,x,y,c;
 fscanf(f,"%d %d %d",&n,&m,&e);
 for(i=1;i<=n;i++)
  {
  G[0].push_back(i);
  Cs[0].push_back(0);
  C[0][i]=1;
  }
 for(i=1;i<=m;i++)
  {
  G[n+i].push_back(n+m+1);
  Cs[n+i].push_back(0);
  C[n+i][n+m+1]=1;
  }
 for(i=1;i<=e;i++)
  {
  fscanf(f,"%d %d %d",&x,&y,&c);
  M[x][n+y]=i;
  G[x].push_back(n+y);
  Cs[x].push_back(c);
  G[n+y].push_back(x);
  Cs[n+y].push_back(-c);
  C[x][n+y]=1;
  }
 }
inline int min(int x,int y)
 {
 if(x<y) return x;
 return y;
 }
bool BF()
 {
 k=-1;
 int c=3;
 int i,x,j,y;
 Q[++k]=0;
 for(i=0;i<=n;i++){drum[i]=inf;pre[i]=-1;}
 drum[0]=0;
 viz[0]=true;
 for(i=0;i<=k;i++)
  {
  x=Q[i];
  for(j=0;j<G[x].size();j++)
   {
   y=G[x][j];
   c=Cs[x][j];
   if(C[x][y]-F[x][y]>0&&drum[y]>drum[x]+c)
    {
    drum[y]=drum[x]+c;
	pre[y]=x;
	if(!viz[y])
	 {
	 viz[y]=true;
	 Q[++k]=y;
	 }
    }
   }
  viz[x]=false;
  }
 if(drum[n]!=inf)
  {
  c=3;
  for(i=n;pre[i]!=-1;i=pre[i])
   c=min(c,C[pre[i]][i]-F[pre[i]][i]);
  for(i=n;pre[i]!=-1;i=pre[i])
   {
   F[pre[i]][i]+=c;
   F[i][pre[i]]-=c;
   }
  }
 return drum[n]!=inf;
 }
void flux()
 {
 bool drum=false;
 do
  {
  drum=BF();
  }while(drum);
 }
void show()
 {
 long long cost=0;
 int nv=0;
 k=-1;
 int i,j;
 for(i=1;i<=n-m-1;i++)
  for(j=0;j<G[i].size();j++)
   {
   if(F[i][G[i][j]])
    {
    ++nv;
	cost+=Cs[i][j];
	sol[++k]=M[i][G[i][j]];
    }
   }
 fprintf(fout,"%d %lld\n",nv,cost);
 for(i=0;i<=k;i++)
  fprintf(fout,"%d ",sol[i]);
 }
int main()
 {
 read();
 n=n+m+1;
 flux();
 show();
 return 0;
 }