Problem p00897 (C++) — buggy submission, verdict: Time Limit Exceeded

#include <algorithm>
#include <bitset>
#include <cmath>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <ctime>
#include <deque>
#include <fstream>
#include <functional>
#include <iomanip>
#include <iostream>
#include <list>
#include <map>
#include <numeric>
#include <queue>
#include <set>
#include <sstream>
#include <stack>
#include <utility>
#include <vector>
using namespace std;
int n, m, l, qq;
#define MAXN 6001
vector<pair<int, int>> a[MAXN], b[MAXN];
const int inf = 0x7fffffff;
int d[MAXN];
bool bo[MAXN], p[MAXN];
map<string, int> hash;
void spfa(int s) {
  for (int i = 0; i <= n; ++i) {
    d[i] = inf;
  }
  memset(bo, 0, sizeof(bo));
  d[s] = 0;
  bo[s] = 1;
  queue<int> q;
  q.push(s);
  while (!q.empty()) {
    int now = q.front();
    q.pop();
    bo[now] = 0;
    for (int i = 0; i < a[now].size(); ++i) {
      int v = a[now][i].first;
      int abc = a[now][i].second;
      if (d[v] - abc > d[now]) {
        d[v] = abc + d[now];
        if (!bo[v]) {
          bo[v] = 1;
          q.push(v);
        }
      }
    }
  }
}

void spfa2(int s) {
  for (int i = 0; i <= n; ++i) {
    d[i] = inf;
  }
  memset(bo, 0, sizeof(bo));
  d[s] = 0;
  bo[s] = 1;
  queue<int> q;
  q.push(s);
  while (!q.empty()) {
    int now = q.front();
    q.pop();
    bo[now] = 0;
    for (int i = 0; i < b[now].size(); ++i) {
      int v = b[now][i].first;
      int abc = b[now][i].second;
      if (d[v] - abc > d[now]) {
        d[v] = abc + d[now];
        if (!bo[v]) {
          bo[v] = 1;
          q.push(v);
        }
      }
    }
  }
}
string temp, temp2;
int main(int argc, char const *argv[]) {
  // freopen("input.txt","r",stdin);
  while (scanf("%d%d%d", &m, &qq, &l) != EOF) {
    if (m == 0 && qq == 0 && l == 0)
      break;
    hash.clear();
    l *= 10;
    for (int i = 0; i < MAXN; ++i) {
      a[i].clear();
      b[i].clear();
    }
    memset(p, 0, sizeof(p));
    n = 0;
    int s, t;
    cin >> temp;
    if (!hash.count(temp)) {
      hash[temp] = ++n;
    }
    s = hash[temp];
    cin >> temp;
    if (!hash.count(temp)) {
      hash[temp] = ++n;
    }
    t = hash[temp];
    for (int i = 0; i < m; ++i) {
      cin >> temp >> temp2;
      int x, y, z;
      if (!hash.count(temp)) {
        hash[temp] = ++n;
      }
      if (!hash.count(temp2)) {
        hash[temp2] = ++n;
      }
      x = hash[temp];
      y = hash[temp2];
      cin >> z;
      if (z <= l) {
        a[x].push_back(make_pair(y, z));
        a[y].push_back(make_pair(x, z));
        // cout<<x<<' '<<y<<' '<<z<<endl;
      }
    }
    int ans = inf;

    for (int i = 0; i < qq; ++i) {
      cin >> temp;
      if (!hash.count(temp)) {
        hash[temp] = ++n;
      }
      int x = hash[temp];
      p[x] = 1;
    }
    for (int i = 0; i <= n; ++i) {
      if (p[i]) {
        spfa(i);
        // cout<<i<<endl;
        for (int j = 1; j <= n; ++j) {
          if (d[j] <= l && j != i && (p[j] || j == t)) {
            b[i].push_back(make_pair(j, d[j]));
            b[j].push_back(make_pair(i, d[j]));
          }
        }
      }
    }
    spfa(s);
    for (int j = 1; j <= n; ++j) {
      if (d[j] <= l && j != s && (p[j] || j == t)) {
        b[s].push_back(make_pair(j, d[j]));
        b[j].push_back(make_pair(s, d[j]));
      }
    }
    /*for (int i = 1; i <=n; ++i)
    {
        for (int j = 0; j < b[i].size(); ++j)
        {
            cout<<i<<" "<<b[i][j].first<<' '<<b[i][j].second<<endl;
        }
        cout<<endl;
    }*/
    spfa2(s);
    // cout<<s<<' '<<t<<endl;
    ans = d[t];
    if (ans == inf) {
      puts("-1");
    } else {
      printf("%d\\n", ans);
    }
  }
  return 0;
}

Error: TLE

Fixed submission:

// Hello. I'm Peter.
#include <algorithm>
#include <cctype>
#include <cmath>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <ctime>
#include <deque>
#include <functional>
#include <iomanip>
#include <iostream>
#include <limits>
#include <map>
#include <queue>
#include <set>
#include <sstream>
#include <stack>
#include <string>
#include <vector>
using namespace std;
#define input freopen("data.txt", "r", stdin)
#define output freopen("output.txt", "w", stdout)
#define INT (0x3f3f3f3f) * 2
#define LL (0x3f3f3f3f3f3f3f3f) * 2
#define clr(a) memset(a, 0, sizeof(a))
#define clr_minus1(a) memset(a, -1, sizeof(a))
#define clr_NULL(a) memset(a, NULL, sizeof(a))
#define clr_INT(a) memset(a, INT, sizeof(a))
#define clr_true(a) memset(a, true, sizeof(a))
#define clr_false(a) memset(a, false, sizeof(a))
#define clr_queue(q)                                                           \\
  while (!q.empty())                                                           \\
  q.pop()
#define clr_stack(s)                                                           \\
  while (!s.empty())                                                           \\
  s.pop()
#define rep(i, a, b) for (int i = a; i < b; i++)
#define dep(i, a, b) for (int i = a; i > b; i--)
#define repin(i, a, b) for (int i = a; i <= b; i++)
#define depin(i, a, b) for (int i = a; i >= b; i--)
#define ll long long
#define eps
#define MOD
#define MAXN
#define N 3010
#define M
struct Pre {
  int cost;
  int realcost;
} pre[N][N];
int len[N];
struct Vertex {
  int realcost;
  int cost;
  int id;
  friend bool operator<(const Vertex a, const Vertex b) {
    if (a.cost != b.cost)
      return a.cost > b.cost;
    else
      return a.realcost > b.realcost;
  }
} v, newv, vt;
priority_queue<Vertex> q;
struct Edge {
  int from;
  int next;
  int to;
  int cost;
} edge[2 * N];
bool oil[N];
int head[N];
int cost[N];
int realcost[N];
int n, m, cap;
int mostdis;
int ans;
map<string, int> m1;
map<int, string> m2;
string sta;
string des;
bool is_ok(int id, int nowcost, int nowrealcost) {
  int l = len[id];
  if (l == 0)
    return true;
  repin(i, 1, l) {
    if (nowcost >= pre[id][i].cost && nowrealcost >= pre[id][i].realcost)
      continue;
    return true;
  }
  return false;
}
void dijkstra() {
  clr_queue(q);
  v.id = 1;
  v.cost = 0;
  v.realcost = 0;
  q.push(v);
  clr_INT(cost);
  cost[1] = 0;
  clr_INT(realcost);
  cost[1] = 0;
  int i, now, to, cos;
  clr(len);
  len[1]++;
  pre[1][len[1]].cost = 0;
  pre[1][len[1]].realcost = 0;
  while (!q.empty()) {
    v = q.top();
    q.pop();
    now = v.id;
    for (i = head[now]; i != -1; i = edge[i].next) {
      to = edge[i].to;
      cos = edge[i].cost;
      if (v.cost + cos <= mostdis) {
        newv.id = to;
        newv.cost = v.cost + cos;
        if (oil[to])
          newv.cost = 0;
        newv.realcost = v.realcost + cos;
        if (!is_ok(to, newv.cost, newv.realcost))
          continue;
        q.push(newv);
        len[to]++;
        pre[to][len[to]].cost = newv.cost;
        pre[to][len[to]].realcost = newv.realcost;
      }
    }
  }
}
int main() {
  //    input;
  string cc1, cc2;
  int d, w, a, c1 = 1, c2 = 1, t;
  while (~scanf("%d %d %d", &n, &m, &cap) && (n + m + cap)) {
    mostdis = cap * 10;
    w = 0;
    a = 0;
    clr_minus1(head);
    m1.clear();
    m2.clear();
    cin >> sta >> des;
    a++;
    m1[sta] = a;
    m2[a] = sta;
    a++;
    m1[des] = a;
    m2[a] = des;
    repin(i, 1, n) {
      cin >> cc1 >> cc2;
      if (!m1[cc1]) {
        a++;
        c1 = a;
        m1[cc1] = a;
        m2[a] = cc1;
      } else
        c1 = m1[cc1];
      if (!m1[cc2]) {
        a++;
        c2 = a;
        m1[cc2] = a;
        m2[a] = cc2;
      } else
        c2 = m1[cc2];
      scanf("%d", &d);
      edge[w].from = c1;
      edge[w].to = c2;
      edge[w].cost = d;
      edge[w].next = head[c1];
      head[c1] = w++;

      edge[w].from = c2;
      edge[w].to = c1;
      edge[w].cost = d;
      edge[w].next = head[c2];
      head[c2] = w++;
    }
    clr_false(oil);
    repin(i, 1, m) {
      cin >> cc1;
      t = m1[cc1];
      oil[t] = true;
    }
    dijkstra();
    ans = INT;
    repin(i, 1, len[2]) { ans = min(ans, pre[2][i].realcost); }
    if (ans == INT)
      cout << -1 << endl;
    else
      cout << ans << endl;
  }
}