#include <bits/stdc++.h>
#define f1(i, j, n) for (int i = (j); i < (n); i++)
#define f2(i, j, n) for (int i = (j); i > (n); i--)
#define endl "\n"
using namespace std;
typedef long long ll;
const int maxn = 1e5 + 10;
struct node {
ll h;
int f;
int x, y;
} a[505][505];
int flag[505][505];
int dx[4] = {1, -1, 0, 0}, dy[4] = {0, 0, 1, -1};
int n, m;
ll ans;
int sx = -1, sy = -1;
queue<node> q;
bool check(int x, int y) {
if (x < 1 || y < 1 || x > n || y > m || flag[x][y]) return false;
return true;
}
bool bfs(ll d, int g) {
memset(flag, 0, sizeof(flag));
int cnt = 1;
q.push(a[sx][sy]);
flag[sx][sy] = 1;
while (!q.empty()) {
node e = q.front();
q.pop();
if (cnt == g) return true;
f1(i, 0, 4) {
int nx = e.x + dx[i], ny = e.y + dy[i];
if (check(nx, ny)) {
ll sd = abs(a[nx][ny].h - e.h);
if (sd > d)
continue;
else {
if (a[nx][ny].f) cnt++;
q.push(a[nx][ny]);
flag[nx][ny] = 1;
}
}
}
}
return false;
}
int main() {
cin >> n >> m;
ll l = 0, r = 0, t = 0;
f1(i, 1, n + 1) f1(j, 1, m + 1) {
cin >> a[i][j].h;
a[i][j].x = i;
a[i][j].y = j;
r = max(r, a[i][j].h);
}
f1(i, 1, n + 1) f1(j, 1, m + 1) {
cin >> a[i][j].f;
if (a[i][j].f) {
t++;
if (sx == -1) sx = i, sy = j;
}
}
while (l <= r) {
ll mid = (l + r) / 2;
if (bfs(mid, t)) {
r = mid - 1;
ans = mid;
} else {
l = mid + 1;
}
}
cout << ans;
}