Cod sursa(job #152022)

Utilizator blasterzMircea Dima blasterz Data 8 martie 2008 22:44:10
Problema Paznici2 Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.51 kb
using namespace std;
#include <cstdio>
#include <string>
#include <queue>
#define maxn 405
#define oo 0x3f3f3f3f
int cost[maxn][maxn],cap[maxn][maxn];
bool inq[maxn];
int n;
int source, sink;
int d[maxn], t[maxn];

void read()
{
	freopen("paznici2.in","r",stdin);
	scanf("%d\n", &n);
	source=0;
	sink=2*n+1;
	int i,j,v;
	for(i=1;i<=n;++i)
		for(j=n+1;j<sink;++j)
		{
			scanf("%d ", &v);
			cost[i][j]=v;
			cost[j][i]=-v;
			cap[i][j]=1;
		}

	for(i=1;i<=n;++i) cap[source][i]=1;
	for(i=n+1;i<sink;++i) cap[i][sink]=1;
}

inline int bell(int s)
{
	int u, i;
	queue<int>Q;
	memset(d, oo, sizeof(d));
	memset(t, 0,sizeof(t));
	memset(inq, 0,sizeof(inq));
	d[s]=0;
	Q.push(s);
	inq[s]=1;
	
	while(!Q.empty())
	{
		u=Q.front();
		Q.pop();
		inq[u]=0;
		
		for(i=source;i<=sink;++i)
			if(cap[u][i])
				if(d[u]+cost[u][i]<d[i])
				{
					d[i]=d[u]+cost[u][i];
					t[i]=u;
					if(!inq[i]) {Q.push(i); inq[i]=1;}
				}
	}

	
	if(t[sink]==0) return 0;
	return 1;
	
}

void solve()
{
	int sol=0,i,j;


	while(bell(source))
	{
	
		sol+=d[sink];
		for(i=sink; i!=source; i=t[i])
			--cap[t[i]][i],
			++cap[i][t[i]];
	}
		
	printf("%d\n",sol);
	int s[maxn], ns=0;
	
	for(i=n+1;i<sink;++i)
	{
		bell(i);
		ns=0;
		for(j=1;j<=n;++j)
			if(cost[j][i]+d[j]==0) s[++ns]=j;
		
		printf("%d ", ns);
		for(j=1;j<=ns;++j)printf("%d ", s[j]);
		printf("\n");
	}
	
}


int main()
{
	
	read();
	freopen("paznici2.out","w",stdout);
	solve();
	
	return 0;
}