首页 > 代码库 > HDU 4975 A simple Gaussian elimination problem.
HDU 4975 A simple Gaussian elimination problem.
http://acm.hdu.edu.cn/showproblem.php?pid=4975
题意:同HDU 4888。给N行M列,每行之和,每列之和,判断矩阵是不是唯一。
题解:网络流。源点和每行之和建边,容量为和;汇点和没列之和建边,容量为和;行之和和列之和建边,容量为9(每位只能是0~9)。
判断可行性:行之和的和是否等于列之和的和;是否满流。
判断唯一解:残留网络里是否有长度大于等于2的环
1 #include <cstdio> 2 #include <cstring> 3 #include <iostream> 4 #include <cstdlib> 5 #include <string> 6 #include <algorithm> 7 #include <vector> 8 #include <map> 9 #include <set> 10 #include <queue> 11 #include <stack> 12 #include <cmath> 13 #include <ctime> 14 #include <functional> 15 #include <cctype> 16 17 using namespace std; 18 19 typedef __int64 ll; 20 21 const int INF=0xfffffff; 22 23 const int maxm=500*500*10+10; 24 const int maxn=510+510; 25 26 struct edge{ 27 int to,cap,next; 28 edge(int to=0,int cap=0,int next=0):to(to),cap(cap),next(next){} 29 }G[maxm]; 30 int head[maxn],level[maxn]; 31 bool used[maxn]; 32 int g[maxn][maxn]; 33 int sumr,sumc; 34 int N,M; 35 int flag; 36 int idx; 37 int s,t; 38 39 void add_edge(int from,int to,int cap) 40 { 41 G[++idx]=edge(to,cap,head[from]); 42 head[from]=idx; 43 G[++idx]=edge(from,0,head[to]); 44 head[to]=idx; 45 } 46 47 bool bfs(int S,int T) 48 { 49 memset(level,0xff,sizeof(level)); 50 level[S]=0; 51 queue<int> q; 52 q.push(S); 53 while(!q.empty()) 54 { 55 int v=q.front(); 56 q.pop(); 57 for(int k=head[v];k!=-1;k=G[k].next) 58 { 59 edge &e=G[k]; 60 if(level[e.to]==-1&&e.cap){ 61 level[e.to]=level[v]+1; 62 q.push(e.to); 63 } 64 } 65 } 66 return level[T]!=-1; 67 } 68 69 int dfs(int v,int f,int T) 70 { 71 if(v==T||f==0) return f; 72 int flow=0; 73 for(int k=head[v];k!=-1;k=G[k].next) 74 { 75 edge &e=G[k]; 76 if(level[e.to]==level[v]+1){ 77 int d; 78 if((d=dfs(e.to,min(f,e.cap),T))>0){ 79 G[k].cap-=d; 80 G[k^1].cap+=d; 81 flow+=d; 82 f-=d; 83 if(f==0) return flow; 84 } 85 } 86 } 87 level[v]=-1; 88 return flow; 89 } 90 91 int max_flow(int s,int t) 92 { 93 int flow=0; 94 int f; 95 while(bfs(s,t)==1) 96 { 97 while((f=dfs(s,INF,t))>0) 98 { 99 flow+=f;100 }101 }102 return flow;103 }104 105 int dfs_loop(int u,int rev)106 {107 for(int &k=head[u];k!=-1;k=G[k].next)108 {109 if(k==(rev^1)) continue;110 if(G[k].cap){111 if(used[G[k].to]) return 1;112 used[G[k].to]=true;113 if(dfs_loop(G[k].to,k)==1) return 1;114 used[G[k].to]=false;115 }116 }117 return 0;118 }119 120 int judge()121 {122 for(int i=1;i<=N;i++)123 {124 if(dfs_loop(i,-1)) return 0;125 }126 return 1;127 }128 129 void init()130 {131 idx=-1;132 memset(head,0xff,sizeof(head));133 memset(used,0,sizeof(used));134 sumr=0;135 sumc=0;136 flag=0;137 }138 139 int main() {140 int T;141 scanf("%d",&T);142 for(int ca=1;ca<=T;ca++)143 {144 init();145 printf("Case #%d: ",ca);146 scanf("%d%d",&N,&M);147 s=0;148 t=N+M+1;149 int cr;150 for(int i=1;i<=N;i++)151 {152 scanf("%d",&cr);153 sumr+=cr;154 add_edge(s,i,cr);155 for(int j=1;j<=M;j++)156 {157 add_edge(i,N+j,9);158 }159 }160 int cc;161 for(int i=1;i<=M;i++)162 {163 scanf("%d",&cc);164 sumc+=cc;165 add_edge(N+i,t,cc);166 }167 int maxflow=max_flow(s,t);168 if(sumr!=sumc) puts("So naive!");169 else if(sumr!=maxflow) puts("So naive!");170 else if(!judge()) puts("So young!");171 else puts("So simple!");172 }173 return 0;174 }
HDU 4975 A simple Gaussian elimination problem.
声明:以上内容来自用户投稿及互联网公开渠道收集整理发布,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任,若内容有误或涉及侵权可进行投诉: 投诉/举报 工作人员会在5个工作日内联系你,一经查实,本站将立刻删除涉嫌侵权内容。