Problem p03602 (C++)

Buggy submission (status: Runtime Error):
#include <algorithm>
#include <cmath>
#include <cstdio>
#include <cstdlib>
#include <cstring>
using namespace std;
typedef long long LL;

const int MaxN = 300, MaxM = 300 * 300;
int n, tot, all, g[MaxN + 5][MaxN + 5];
int pre[MaxM + 5], last[MaxN + 5], other[MaxM + 5];
LL cost[MaxM + 5], dis[MaxN + 5];
int seq[MaxN + 5];
bool Inseq[MaxN + 5];
struct EDGE {
  int u, v, w;
} edge[MaxM + 5];

void Build(int x, int y, int w) {
  pre[++all] = last[x];
  last[x] = all;
  other[all] = y;
  cost[all] = w;
}

void Init() {
  tot = 0;
  all = -1;
  memset(last, -1, sizeof(last));
  for (int i = 1; i <= n; i++)
    for (int j = 1; j <= n; j++) {
      scanf("%d", &g[i][j]);
      if (j > i) {
        edge[++tot].u = i;
        edge[tot].v = j;
        edge[tot].w = g[i][j];
      }
    }
}

void spfa(int s) {
  memset(Inseq, 0, sizeof(Inseq));
  for (int i = 1; i <= n; i++)
    dis[i] = 1LL << 50;
  dis[s] = 0;
  Inseq[s] = true;
  int head = 1, tail = 0;
  seq[++tail] = s;
  while (head <= tail) {
    int now = seq[head];
    int ed = last[now], dr;
    while (ed != -1) {
      dr = other[ed];
      if (dis[now] + cost[ed] < dis[dr]) {
        dis[dr] = dis[now] + cost[ed];
        if (!Inseq[dr]) {
          Inseq[dr] = true;
          seq[++tail] = dr;
        }
      }
      ed = pre[ed];
    }
    head++;
    Inseq[now] = false;
  }
}

bool cmp(EDGE A, EDGE B) { return A.w < B.w; }
void Solve() {
  sort(edge + 1, edge + tot + 1, cmp);
  LL ans = 0;
  bool flag = false;
  for (int i = 1; i <= tot; i++) {
    int u = edge[i].u, v = edge[i].v, len = edge[i].w;
    spfa(u);
    if (dis[v] > len)
      Build(u, v, len), Build(v, u, len), ans = ans + len;
    else if (dis[v] < len)
      flag = true;
  }
  if (flag)
    printf("-1\n");
  else
    printf("%lld\n", ans);
}

int main() {
  while (~scanf("%d", &n)) {
    Init();
    Solve();
  }
  return 0;
}

Fixed submission:
#include <algorithm>
#include <cmath>
#include <cstdio>
#include <cstdlib>
#include <cstring>
using namespace std;
typedef long long LL;

const int MaxN = 300, MaxM = 300 * 300;
int n, tot, all, g[MaxN + 5][MaxN + 5];
int pre[MaxM + 5], last[MaxN + 5], other[MaxM + 5];
LL cost[MaxM + 5], dis[MaxN + 5];
int seq[MaxM + 5];
bool Inseq[MaxN + 5];
struct EDGE {
  int u, v, w;
} edge[MaxM + 5];

void Build(int x, int y, int w) {
  pre[++all] = last[x];
  last[x] = all;
  other[all] = y;
  cost[all] = w;
}

void Init() {
  tot = 0;
  all = -1;
  memset(last, -1, sizeof(last));
  for (int i = 1; i <= n; i++)
    for (int j = 1; j <= n; j++) {
      scanf("%d", &g[i][j]);
      if (j > i) {
        edge[++tot].u = i;
        edge[tot].v = j;
        edge[tot].w = g[i][j];
      }
    }
}

void spfa(int s) {
  memset(Inseq, 0, sizeof(Inseq));
  for (int i = 1; i <= n; i++)
    dis[i] = 1LL << 50;
  dis[s] = 0;
  Inseq[s] = true;
  int head = 1, tail = 0;
  seq[++tail] = s;
  while (head <= tail) {
    int now = seq[head];
    int ed = last[now], dr;
    while (ed != -1) {
      dr = other[ed];
      if (dis[now] + cost[ed] < dis[dr]) {
        dis[dr] = dis[now] + cost[ed];
        if (!Inseq[dr]) {
          Inseq[dr] = true;
          seq[++tail] = dr;
        }
      }
      ed = pre[ed];
    }
    head++;
    Inseq[now] = false;
  }
}

bool cmp(EDGE A, EDGE B) { return A.w < B.w; }
void Solve() {
  sort(edge + 1, edge + tot + 1, cmp);
  LL ans = 0;
  bool flag = false;
  for (int i = 1; i <= tot; i++) {
    int u = edge[i].u, v = edge[i].v, len = edge[i].w;
    spfa(u);
    if (dis[v] > len)
      Build(u, v, len), Build(v, u, len), ans = ans + len;
    else if (dis[v] < len)
      flag = true;
  }
  if (flag)
    printf("-1\n");
  else
    printf("%lld\n", ans);
}

int main() {
  while (~scanf("%d", &n)) {
    Init();
    Solve();
  }
  return 0;
}