#include <bits/stdc++.h>

using namespace std;

const int D = 8;

const int dx[D] = {-1, -1, -1, 0, 0, 1, 1, 1};
const int dy[D] = {-1, 0, -1, -1, 1, -1, 0, -1};

vector<vector<int>> Generate(int n, int m, int mask) {
  vector<vector<int>> f(n, vector<int>(m));
  if (mask & 1) {
    f[n - 2][m - 1] = 1;
  }
  if (mask & 2) {
    f[n - 1][m - 1] = 1;
  }
  if (mask & 4) {
    f[n - 2][m - 2] = 1;
  }
  auto Update = [&](int x, int y) {
    if (x + 1 < n) {
      f[x][y] ^= f[x + 1][y];
    }
    if (y + 1 < m) {
      f[x][y] ^= f[x][y + 1];
    }
  };
  auto Valid = [&](int x, int y) {
    return 0 <= x && x < n && 0 <= y && y < m;
  };
  vector<vector<bool>> was(n, vector<bool>(m));
  vector<pair<int, int>> que;
  auto Insert = [&](int x, int y) {
    que.emplace_back(x, y);
    was[x][y] = true;
  };
  Insert(n - 1, m - 1);
  Insert(n - 2, m - 1);
  Insert(n - 2, m - 2);
  auto Free = [&](int x, int y) {
    if (Valid(x, y + 1) && Valid(x - 1, y + 1) && was[x][y + 1] && was[x - 1][y + 1]) {
      Insert(x, y);
      f[x][y] = (f[x][y + 1] ^ f[x - 1][y + 1]);
    } else if (Valid(x + 1, y) && Valid(x + 1, y - 1) && was[x + 1][y] && was[x + 1][y - 1]) {
      Insert(x, y);
      f[x][y] = (f[x + 1][y] ^ f[x + 1][y + 1]);
    } else if (Valid(x + 1, y) && Valid(x, y + 1) && was[x + 1][y] && was[x][y + 1]) {
      Insert(x, y);
      f[x][y] = (f[x + 1][y] ^ f[x][y + 1]);
    }
  };
  for (int b = 0; b < (int) que.size(); b++) {
    int x = que[b].first;
    int y = que[b].second;
    for (int dir = 0; dir < D; dir++) {
      int nx = x + dx[dir];
      int ny = y + dy[dir];
      if (Valid(nx, ny) && !was[nx][ny]) {
        Free(nx, ny);
      }
    }
  }
  return f;
}

int main() {
  ios::sync_with_stdio(false);
  cin.tie(0);
  int n, m;
  cin >> n >> m;
  vector<vector<int>> a(n, vector<int>(m));
  for (int i = 0; i < n; i++) {
    for (int j = 0; j < m; j++) {
      cin >> a[i][j];
    }
  }
  auto Solve = [&](vector<vector<int>> b) {
    int res = 0;
    for (int i = 0; i < n; i++) {
      for (int j = 0; j < m; j++) {
        res += b[i][j];
      }
    }
    if (n == 1 || m == 1) {
      return min(res, n * m - res);
    }
    vector<int> cnt(n + m);
    for (int i = 0; i < n; i++) {
      for (int j = 0; j < m; j++) {
        cnt[i + j] += b[i][j];
      }
    }
    for (int par = 0; par < 2; par++) {
      int cc = 0;
      for (int i = 0; i <= n + m - 2; i++) {
        cc += (par != (cnt[i] % 2));
      }
      res = min(res, cc);
    }
//    for (int mask = 0; mask < 8; mask++) {
//      vector<vector<int>> f = Generate(n, m, mask);
//      int cur = 0;
//      for (int i = 0; i < n; i++) {
//        for (int j = 0; j < m; j++) {
//          cur += (f[i][j] ^ b[i][j]);
//        }
//      }
//      res = min(res, cur);
//    }
    return res;
  };
//  for (int MASK = 0; MASK < 8; MASK++) {
//    cout << "JEBEM TI ZADATAK " << MASK << '\n';
//    auto mat = Generate(n, m, MASK);
//    for (int i = 0; i < n; i++) {
//      for (int j = 0; j < m; j++) {
//        cout << mat[i][j] << " ";
//      }
//      cout << '\n';
//    }
//    cout << "mrs\n";
//  }
  long long ans = 0;
  for (int c = 0; c < 30; c++) {
    vector<vector<int>> b(n, vector<int>(m));
    for (int i = 0; i < n; i++) {
      for (int j = 0; j < m; j++) {
        if (a[i][j] >> c & 1) {
          b[i][j] = 1;
        } else {
          b[i][j] = 0;
        }
      }
    }
    ans += Solve(b) * (1LL << c);
  }
  cout << ans << '\n';
  return 0;
}