M - Cyclic Tour
There are N cities in our country, and Mone-way roads connecting them. Now Little Tom wants to make several cyclictours, which satisfy that, each cycle contain at least two cities, and eachcity belongs to one cycle exactly. Tom wants the total length of all the toursminimum, but he is too lazy to calculate. Can you help him?
Input
There are several test cases in the input. You shouldprocess to the end of file (EOF).
The first line of each test case contains two integers N (N ≤ 100) and M,indicating the number of cities and the number of roads. The M lines followed,each of them contains three numbers A, B, and C, indicating that there is aroad from city A to city B, whose
length is C. (1 ≤ A,B ≤ N, A ≠ B, 1 ≤ C ≤1000).
Output
Output one number for each test case, indicating theminimum length of all the tours. If there are no such tours, output -1.
Sample Input
6 9
1 2 5
2 3 5
3 1 10
3 4 12
4 1 8
4 6 11
5 4 7
5 6 9
6 5 4
6 5
1 2 1
2 3 1
3 4 1
4 5 1
5 6 1
Sample Output
42
-1
Hint
In thefirst sample, there are two cycles, (1->2->3->1) and(6->5->4->6) whose length is 20 + 22 = 42.
#include<stdio.h>
#include<string.h>
int a[120][120],x1[120],y1[120],x2[120],y2[120],match[120],c[120];
int m,n;
int max(int x,int y)
{
if(x<y)
x=y;
return x;
}
int min(int x,int y)
{
if(x>y)
x=y;
return x;
}
int dfs(int w)
{
int i,t;
x2[w]=1;
for(i=1;i<=n;i++)
{
if(y2[i])
continue;
t=x1[w]+y1[i]-a[w][i];
if(t==0)
{
y2[i]=1;
if(match[i]==-1||dfs(match[i]))
{
match[i]=w;
return 1;
}
}
else
{
c[i]=min(c[i],t);
}
}
return 0;
}
void km()
{
int i,j,t;
memset(match,-1,sizeof(match));
memset(y1,0,sizeof(y1));
for(i=1;i<=n;i++)
{
x1[i]=a[i][1];
for(j=2;j<=n;j++)
{
x1[i]=max(x1[i],a[i][j]);
}
}
for(i=1;i<=n;i++)
{
for(j=1;j<=n;j++)
c[j]=1e9;
while(1)
{
memset(x2,0,sizeof(x2));
memset(y2,0,sizeof(y2));
if(dfs(i))
break;
t=1e9;
for(j=1;j<=n;j++)
{
if(!y2[j]&&t>c[j])
t=c[j];
}
for(j=1;j<=n;j++)
{
if(x2[j])
x1[j]-=t;
}
for(j=1;j<=n;j++)
{
if(y2[j])
y1[j]+=t;
else
c[j]-=t;
}
}
}
int sum=0,f=0;
for(i=1;i<=n;i++)
{
if(match[i]==-1||a[match[i]][i]==-1e9)//注意判断是否将全部的点加入
{
f=1;
break;
}
sum+=a[match[i]][i];
}
if(f==1)
{
printf("-1\n");
}
else
printf("%d\n",-sum);
}
int main()
{
int i,j,k;
int t1,t2,t3;
while(scanf("%d%d",&n,&m)!=EOF)
{
for(i=1;i<=n;i++)
{
for(j=1;j<=n;j++)
a[i][j]=-1e9;
}
for(i=1;i<=m;i++)
{
scanf("%d%d%d",&t1,&t2,&t3);
if(t3<-a[t1][t2])
{
a[t1][t2]=-t3;
}
}
/* for(i=1;i<=n;i++)
{
for(j=1;j<=n;j++)
{
printf("%d ",a[i][j]);
}
printf("\n");
}
*/ km();
}
return 0;
}