#include <bits/stdc++.h>   using namespace std;   const int MAXN = 7007;   const int MAXM = 300007;   const int INF = 1 << 29;   const int dir[][2] = {{0, 1}, {0, -1}, {1, 0}, {-1, 0}};   char reactor[15][15], rescue[15][15];   int N;   int table[15][15];   bool isIn(int x, int y) { return x >= 1 && y >= 1 && x <= N && y <= N; }   struct Edge {     int u, v, cap, flow;     Edge *next, *back;   };   struct Graph {     Edge *head[MAXN], adj[MAXM];     Edge *cur[MAXN], *path[MAXN];     int lev[MAXN];     int n, k;     int S, T;     void init(int nn) {       S = 0, T = nn;       n = nn, k = 0;       for (int i = 0; i <= n; i++) head[i] = NULL;     }     void set(int s, int t) { S = s, T = t; }     void addedge(int u, int v, int cap) {       adj[k].u = u;       adj[k].v = v;       adj[k].flow = 0;       adj[k].cap = cap;       adj[k].next = head[u];       head[u] = adj + k++;     }     void add(int u, int v, int cap) {       addedge(u, v, cap);       addedge(v, u, 0);       head[u]->back = head[v];       head[v]->back = head[u];     }     bool bfs() {       queue<int> q;       fill(lev, lev + n + 1, -1);       lev[S] = 0;       q.push(S);       int u, v;       while (!q.empty()) {         u = q.front();         q.pop();         for (Edge *f = head[u]; f; f = f->next) {           if (f->flow == f->cap) continue;           v = f->v;           if (lev[v] == -1) {             lev[v] = lev[u] + 1;             q.push(v);             if (v == T) return true;           }         }       }       return (lev[T] != -1);     }     int dinic() {       int u, v, pt;       int flow = 0;       while (bfs()) {         for (int i = 0; i <= n; i++) cur[i] = head[i];         pt = 0;         u = S;         while (true) {           if (u == T) {             int delta = INF, minI = 0;             for (int i = 0; i < pt; i++) {               if (delta > path[i]->cap - path[i]->flow) {                 delta = path[i]->cap - path[i]->flow;                 minI = i;               }             }             for (int i = 0; i < pt; i++) {               path[i]->flow += delta;               path[i]->back->flow -= delta;             }             u = path[pt = minI]->u;             flow += delta;           }           Edge *f;           for (f = cur[u]; f; f = f->next) {             if (f->cap == f->flow) continue;             v = f->v;             if (lev[v] == lev[u] + 1) break;           }           cur[u] = f;           if (f) {             path[pt++] = f;             u = f->v;           } else {             lev[u] = -1;             if (!pt) break;             u = path[--pt]->u;           }         }       }       return flow;     }   } graph;   void bfs(int sx, int sy, int t) {     for (int i = 1; i <= N; i++) {       fill(table[i], table[i] + N + 1, INF);     }     queue<pair<int, int> > q;     q.push(pair<int, int>(sx, sy));     table[sx][sy] = 0;     while (!q.empty()) {       pair<int, int> cur = q.front();       q.pop();       for (int i = 0; i < 4; i++) {         int x = cur.first + dir[i][0];         int y = cur.second + dir[i][1];         if (!isIn(x, y) || !isdigit(reactor[x][y]) || table[x][y] != INF) {           continue;         }         table[x][y] = table[cur.first][cur.second] + 1;         q.push(pair<int, int>(x, y));       }     }   }   int main() {     int n, t;     int S, T;     scanf( %d%d , &n, &t);     N = n;     int sx, sy;     for (int i = 1; i <= n; i++) {       scanf(  %s , reactor[i] + 1);       for (int j = 1; j <= n; j++) {         if (reactor[i][j] ==  Z ) {           sx = i;           sy = j;         }       }     }     bfs(sx, sy, t);     for (int i = 1; i <= n; i++) {       scanf(  %s , rescue[i] + 1);     }     S = 0, T = (t + 1) * n * n + 1;     graph.init(T);     graph.set(S, T);     for (int cur = 0; cur < t; cur++) {       int add1 = cur * n * n;       int add2 = (cur + 1) * n * n;       for (int i = 1; i <= n; i++) {         for (int j = 1; j <= n; j++) {           if (!isdigit(reactor[i][j])) continue;           if (isdigit(rescue[i][j]) && rescue[i][j] !=  0 ) {             graph.add(add1 + (i - 1) * n + j, add2 + (i - 1) * n + j,                       rescue[i][j] -  0 );             if (cur >= table[i][j]) continue;           }           if (isdigit(reactor[i][j]) && cur < table[i][j]) {             if (cur + 1 < table[i][j]) {               graph.add(add1 + (i - 1) * n + j, add2 + (i - 1) * n + j, INF);             }             for (int k = 0; k < 4; k++) {               int x = i + dir[k][0];               int y = j + dir[k][1];               if (!isIn(x, y) || !isdigit(reactor[x][y])) continue;               if (cur + 1 < table[x][y] ||                   table[x][y] == cur + 1 && isdigit(rescue[x][y]))                 graph.add(add1 + (i - 1) * n + j, add2 + (x - 1) * n + y, INF);             }           }         }       }     }     for (int i = 1; i <= n; i++) {       for (int j = 1; j <= n; j++) {         if (isdigit(reactor[i][j]) && reactor[i][j] !=  0 ) {           graph.add(S, (i - 1) * n + j, reactor[i][j] -  0 );         }         if (isdigit(rescue[i][j]) && rescue[i][j] !=  0 ) {           graph.add(t * n * n + (i - 1) * n + j, T, rescue[i][j] -  0 );         }       }     }     printf( %d n , graph.dinic());     return 0;   }