P1129 [ZJOI2007]矩阵游戏 【最大流】

 

 思路

  因为不需要保证只有主对角线上有黑块

  所以这是道蓝题

  那么只要由让 S -> Line[i],Row[j] ->T

  在i == j 时给行列上连边即可

  注意下因为不用保证只有主对角线上才有黑块

  所以这样跑出来的Maxflow是有可能大于n的

  注意一下输出条件即可

CODE

  1 #include <bits/stdc++.h>
  2 #define dbg(x) cout << #x << "=" << x << endl
  3 #define eps 1e-8
  4 #define pi acos(-1.0)
  5 
  6 using namespace std;
  7 typedef long long LL;
  8 
  9 const int inf = 0x3f3f3f3f;
 10 
 11 template<class T>inline void read(T &res)
 12 {
 13     char c;T flag=1;
 14     while((c=getchar())<'0'||c>'9')if(c=='-')flag=-1;res=c-'0';
 15     while((c=getchar())>='0'&&c<='9')res=res*10+c-'0';res*=flag;
 16 }
 17 
 18 namespace _buff {
 19     const size_t BUFF = 1 << 19;
 20     char ibuf[BUFF], *ib = ibuf, *ie = ibuf;
 21     char getc() {
 22         if (ib == ie) {
 23             ib = ibuf;
 24             ie = ibuf + fread(ibuf, 1, BUFF, stdin);
 25         }
 26         return ib == ie ? -1 : *ib++;
 27     }
 28 }
 29 
 30 int qread() {
 31     using namespace _buff;
 32     int ret = 0;
 33     bool pos = true;
 34     char c = getc();
 35     for (; (c < '0' || c > '9') && c != '-'; c = getc()) {
 36         assert(~c);
 37     }
 38     if (c == '-') {
 39         pos = false;
 40         c = getc();
 41     }
 42     for (; c >= '0' && c <= '9'; c = getc()) {
 43         ret = (ret << 3) + (ret << 1) + (c ^ 48);
 44     }
 45     return pos ? ret : -ret;
 46 }
 47 
 48 const int maxn = 200007;
 49 
 50 int n, m;
 51 int s, t;
 52 
 53 struct edge{
 54     int from,to;
 55     LL cap,flow;
 56 };
 57 
 58 map<int, int> vis;
 59 
 60 struct DINIC {
 61     int head[maxn << 1], nxt[maxn << 1], edge[maxn << 1], cnt;
 62     int cap[maxn << 1], depth[maxn << 1];
 63 
 64     void init() {
 65         cnt = 1;
 66         memset(head, 0, sizeof(head));
 67     }
 68 
 69     void BuildGraph(int u, int v, int w) {
 70         ++cnt;
 71         edge[cnt] = v;
 72         nxt[cnt] = head[u];
 73         cap[cnt] = w;
 74         head[u] = cnt;
 75 
 76         ++cnt;
 77         edge[cnt] = u;
 78         nxt[cnt] = head[v];
 79         cap[cnt] = 0;
 80         head[v] = cnt;
 81     }
 82 
 83     queue<int> q;
 84 
 85     bool bfs() {
 86         memset(depth, 0, sizeof(depth));
 87         depth[s] = 1;
 88         q.push(s);
 89         while(!q.empty()) {
 90             int u = q.front();
 91             q.pop();
 92             for ( int i = head[u]; i; i = nxt[i] ) {
 93                 int v = edge[i];
 94                 if(depth[v]) {
 95                     continue;
 96                 }
 97                 if(cap[i]) {
 98                     depth[v] = depth[u] + 1;
 99                     q.push(v);
100                 }
101             }
102         }
103         return depth[t];
104     }
105 
106     int dfs(int u, int dist) {
107         if(u == t) {
108             return dist;
109         }
110         int flow = 0;
111         for ( int i = head[u]; i && dist; i = nxt[i] ) {
112             if(cap[i] == 0)
113                 continue;
114             int v = edge[i];
115             if(depth[v] != depth[u] + 1) {
116                 continue;
117             }
118             int res = dfs(v, min(cap[i], dist));
119             cap[i] -= res;
120             cap[i ^ 1] += res;
121             //printf("cap[%d]:%d\n",t, cap[t]);
122             dist -= res;
123             flow += res;
124         }
125         return flow;
126     }
127 
128     int maxflow() {
129         int ans = 0;
130         while(bfs()) {
131             ans += dfs(s, inf);
132         }
133         return ans;
134     }
135 } dinic;
136 
137 int main()
138 {
139     //freopen("data.txt", "r", stdin);
140     int T;
141     read(T);
142     while(T--) {
143         read(n);
144         dinic.init();
145         s = 0, t = n * 2 + 1;
146         int x;
147         for ( int i = 1; i <= n; ++i ) {
148             dinic.BuildGraph(s, i, 1);
149             dinic.BuildGraph(n + i, t, 1);
150             for ( int j = 1; j <= n; ++j ) {
151                 read(x);
152                 if(x == 1) {
153                     dinic.BuildGraph(i, n + j, 1);
154                 }
155             }
156         }
157         int ans = dinic.maxflow();
158         //dbg(ans);
159         if(ans < n) {
160             puts("No");
161         }
162         else {
163             puts("Yes");
164         }
165     }
166     return 0;
167 }
View Code

猜你喜欢

转载自www.cnblogs.com/orangeko/p/12902672.html