#include <bits/stdc++.h>
using namespace std;
const int maxn = 2005, maxm = 4000005;
struct edge {
  int u, v, w, next;
  edge() {}
  edge(int u, int v, int w, int next) : u(u), v(v), w(w), next(next) {}
  friend bool operator<(const edge &a, const edge &b) { return a.w < b.w; }
} e[maxm], te[maxm];
int tmcnt, link[maxn], mat[maxn][maxn], tmat[maxn][maxn], f[maxn];
int find(int x) { return f[x] == x ? x : f[x] = find(f[x]); }
void add(int u, int v, int w) {
  te[tmcnt] = edge(u, v, w, link[u]);
  link[u] = tmcnt++;
}
void dfs(int x, int fa, int y, int t) {
  tmat[t][x] = y;
  for (int i = link[x]; ~i; i = te[i].next)
    if (te[i].v != fa) dfs(te[i].v, x, y + te[i].w, t);
}
bool solve() {
  int n;
  scanf("%d", &n);
  for (int i = 0; i < n; ++i)
    for (int j = 0; j < n; ++j) {
      scanf("%d", &mat[i][j]);
      if (i == j && mat[i][j]) return false;
      if (i != j && !mat[i][j]) return false;
    }
  int mcnt = 0;
  for (int i = 1; i < n; ++i)
    for (int j = 0; j < i; ++j) e[mcnt++] = edge(i, j, mat[i][j], 0);
  sort(e, e + mcnt);
  for (int i = 0; i < n; ++i) f[i] = i;
  int cnt = 0;
  memset(tmat, -1, sizeof(tmat));
  tmcnt = 0;
  memset(link, -1, sizeof(link));
  for (int i = 0; i < mcnt; ++i) {
    int u = find(e[i].u), v = find(e[i].v);
    if (u != v) {
      f[u] = v;
      ++cnt;
      add(e[i].u, e[i].v, e[i].w);
      add(e[i].v, e[i].u, e[i].w);
    }
    if (cnt == n - 1) break;
  }
  for (int i = 0; i < n; ++i) dfs(i, -1, 0, i);
  for (int i = 0; i < n; ++i)
    for (int j = 0; j < n; ++j)
      if (mat[i][j] != tmat[i][j]) return false;
  return true;
}
int main() {
  if (solve())
    puts("YES");
  else
    puts("NO");
  return 0;
}
