4WA 60tps
#include <bits/stdc++.h>
using namespace std;
const int dx[] = {-1, 0, 1, 0};
const int dy[] = {0, 1, 0, -1};
const int N = 1e7 + 10, M = 110, INF = 1e9;
int a[M][M];
int h[N], tmp[N], e[N], w[N], ne[N], idx;
int d[N];
int maxFlow;
int n, m;
int turn(int x, int y)
{
return (x - 1) * m + y;
}
void add(int a, int b, int c)
{
e[idx] = b, w[idx] = c, ne[idx] = h[a], h[a] = idx++;
e[idx] = a, w[idx] = 0, ne[idx] = h[b], h[b] = idx++;
}
bool bfs(int s, int T)
{
for (int i = 0; i <= n * m + 1; i++) d[i] = -1;
queue<int> q;
q.push(s);
d[s] = 0;
while (q.size())
{
int t = q.front();
q.pop();
tmp[t] = h[t];
for (int i = h[t]; ~i; i = ne[i])
{
int j = e[i];
if (w[i] && d[j] == -1)
{
q.push(j);
d[j] = d[t] + 1;
if (j == T) return true;
}
}
}
return false;
}
int dinic(int u, int flow, int T)
{
if (u == T) return flow;
int left = flow;
for (int i = tmp[u]; ~i; i = ne[i])
{
int j = e[i];
tmp[u] = i;
if (w[i] && d[j] == d[u] + 1)
{
int inc = dinic(j, min(left, w[i]), T);
if (!inc) d[j] = -1;
w[i] -= inc;
w[i ^ 1] += inc;
left -= inc;
}
if (!left) break;
}
return flow - left;
}
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
cout.tie(0);
cin >> n >> m;
int s = 0, t = n * m + 1;
for (int i = 1; i <= n; i++)
for (int j = 1; j <= m; j++)
cin >> a[i][j];
for (int i = 0; i <= n * m * 5; i++) h[i] = -1;
for (int i = 1; i <= n; i++)
for (int j = 1; j <= m; j++)
if (a[i][j] == 1)
add(s, turn(i, j), INF);
else if (a[i][j] == 2)
add(turn(i, j), t, INF);
for (int i = 1; i <= n; i++)
for (int j = 1; j <= m; j++)
for (int k = 0; k < 4; k++)
{
int a = i + dx[k], b = j + dy[k];
if (a > 0 && a <= n && b > 0 && b <= m)
add(turn(i, j), turn(a, b), 1);
}
int res = 0;
while (bfs(s, t))
res += dinic(s, INF, t);
cout << res;
return 0;
}