每个点在且仅在一个有向圈内,所以出读入度卡死为一,裂点为出度控制点和入度控制点……
#include <algorithm> #include <iostream> #include <fstream> #include <sstream> #include <iomanip> #include <map> #include <set> #include <list> #include <stack> #include <queue> #include <deque> #include <vector> #include <string> #include <bitset> #include <memory> #include <complex> #include <numeric> #include <stdio.h> #include <stdlib.h> #include <string.h> #include <math.h> #include <time.h> #include <ctype.h> #include <locale.h> using namespace std; #pragma pack(4) const double eps = 1e-8; const double pi = acos(-1.0); const int inf = 0x7f7f7f7f; const __int64 INF = 0x7f7f7f7f7f7f7f7fll; #define at(a,i) ((a)&(1<<(i))) #define nt(a,i) ((a)^(1<<(i))) #define set1(a,i) ((a)|(1<<(i))) #define set0(a,i) ((a)&(~(1<<(i)))) #define gret(a,b) (((a)-(b))>eps) #define less(a,b) (((b)-(a))>eps) #define greq(a,b) (((a)-(b))>-eps) #define leeq(a,b) (((b)-(a))>-eps) #define equl(a,b) (fabs((a)-(b))<eps) #define lmax(a,b) ((a)>(b)?(a):(b)) #define lmin(a,b) ((a)<(b)?(a):(b)) #define fmax(a,b) (gret(a,b)?(a):(b)) #define fmin(a,b) (less(a,b)?(a):(b)) const int MAXV = 240; const int MAXE = 24000; struct node { int v,w,c; node(int _v=0,int _w=0,int _c=0): v(_v),w(_w),c(_c){} bool operator < (const node argu) const { return w<argu.w; } }G[MAXE]; int _index,pre[MAXV],next[MAXE]; void clear(void) { _index=0; memset(pre,-1,sizeof(pre)); } void add(int u,int v,int w=0,int c=0) { G[_index].v=v; G[_index].w=w; G[_index].c=c; next[_index]=pre[u]; pre[u]=_index++; G[_index].v=u; G[_index].w=0; G[_index].c=-c; next[_index]=pre[v]; pre[v]=_index++; } bool inQ[MAXV]; int dis[MAXV],Q[MAXV],prev[MAXV],curr[MAXV]; int SPFA(int src,int des) { int u,v,w; memset(dis,inf,sizeof(dis)); memset(inQ,false,sizeof(inQ)); dis[Q[0]=src]=0; for(int f=0,r=1;f!=r;f=(f+1)%MAXV) { inQ[u=Q[f]]=false; for(int i=pre[u];i!=-1;i=next[i]) { v=G[i].v; w=G[i].c; if(G[i].w&&dis[v]>dis[u]+w) { dis[v]=dis[u]+w; prev[v]=u; curr[v]=i; if(!inQ[v]) { inQ[Q[r]=v]=true; r=(r+1)%MAXV; } } } } return dis[des]; } int MinCost(int src,int des,int flow) { int cnt,sum=0,tot=0; while(SPFA(src,des)!=inf) { cnt=inf; for(int i=des;i!=src;i=prev[i]) { cnt=min(cnt,G[curr[i]].w); } for(int i=des;i!=src;i=prev[i]) { G[curr[i]].w-=cnt; G[curr[i]^1].w+=cnt; } sum+=(cnt*dis[des]); tot+=cnt; } return tot==flow?sum:-1; } int n,m,u,v,w; int main() { #ifndef ONLINE_JUDGE freopen("Cyclic Tour.txt","r",stdin); #endif while(scanf("%d %d",&n,&m)!=EOF) { clear(); for(int i=0;m>i;i++) { scanf("%d %d %d",&u,&v,&w); add(u,v+n,1,w); } for(int i=0;n>i;i++) { add(0,i+1,1,0); add(i+n+1,n+n+1,1,0); } printf("%d\n",MinCost(0,2*n+1,n)); } return 0; }