#include <bits/stdc++.h>
using namespace std;
struct Tree {
  long long maxv[80005];
  void pushup(int x) { maxv[x] = max(maxv[x << 1], maxv[x << 1 | 1]); }
  void update(int x, int l, int r, int p, long long v) {
    if (l == r) {
      maxv[x] = v;
      return;
    }
    if (p <= ((l + r) >> 1))
      update(x << 1, l, ((l + r) >> 1), p, v);
    else
      update(x << 1 | 1, ((l + r) >> 1) + 1, r, p, v);
    pushup(x);
  }
  long long ask(int x, int l, int r, int from, int to) {
    if (from > to) return -1e12;
    if (l >= from && r <= to) return maxv[x];
    long long ans = -1e12;
    if (from <= ((l + r) >> 1))
      ans = max(ans, ask(x << 1, l, ((l + r) >> 1), from, to));
    if (to > ((l + r) >> 1))
      ans = max(ans, ask(x << 1 | 1, ((l + r) >> 1) + 1, r, from, to));
    return ans;
  }
};
Tree t1, t2, t3;
int n, m, l;
long long a[55][20005], s[55][20005], f[20005];
int main() {
  scanf("%d%d%d", &n, &m, &l);
  for (int i = 1; i <= n; i++)
    for (int j = 1; j <= m; j++) scanf("%lld", &a[i][j]);
  for (int i = 1; i <= n; i++)
    for (int j = 1; j <= m; j++) s[i][j] = s[i][j - 1] + a[i][j];
  for (int i = 1; i <= 80000; i++) t1.maxv[i] = t2.maxv[i] = t3.maxv[i] = -1e12;
  for (int i = 1; i <= n; i++) {
    for (int j = 1; j + l - 1 <= m; j++) {
      f[j] = max(t1.ask(1, 1, m, 1, j - l), t1.ask(1, 1, m, j + l, m));
      f[j] = max(f[j], t2.ask(1, 1, m, j - l + 1, j) + s[i][j - 1]);
      f[j] = max(f[j], t3.ask(1, 1, m, j + 1, j + l) - s[i][j + l - 1]);
      f[j] = max(f[j], 0ll);
    }
    for (int j = 1; j + l - 1 <= m; j++) {
      f[j] = f[j] + s[i][j + l - 1] - s[i][j - 1] + s[i + 1][j + l - 1] -
             s[i + 1][j - 1];
      t1.update(1, 1, m, j, f[j]);
      t2.update(1, 1, m, j, f[j] - s[i + 1][j + l - 1]);
      t3.update(1, 1, m, j, f[j] + s[i + 1][j - 1]);
    }
  }
  printf("%lld\n", t1.ask(1, 1, n, 1, n));
  return 0;
}
