#include <bits/stdc++.h>
using namespace std;
struct edge {
  int x, y, cost;
  edge(int i, int j, int k) {
    x = i;
    y = j;
    cost = k;
  }
};
vector<edge> edges;
inline vector<int> Dijkstra(vector<vector<pair<int, int> > > graph,
                            int start_vertex, int n) {
  vector<int> d(n, 1000000000);
  d[start_vertex] = 0;
  priority_queue<pair<int, int> > q;
  q.push(make_pair(0, start_vertex));
  while (!q.empty()) {
    int v = q.top().second, cur_d = -q.top().first;
    q.pop();
    if (cur_d > d[v]) continue;
    for (unsigned j = 0; j < graph[v].size(); ++j) {
      int to = graph[v][j].first;
      int len = graph[v][j].second;
      if (d[v] + len < d[to]) {
        d[to] = d[v] + len;
        q.push(make_pair(-d[to], to));
      }
    }
  }
  return d;
}
inline int getAnswer(vector<int> d, int l, int n, int m) {
  int ans = 0;
  for (int i = 0; i < n; ++i)
    if (d[i] == l) ans++;
  for (int i = 0; i < m; ++i) {
    int u = edges[i].x;
    int v = edges[i].y;
    int w = edges[i].cost;
    if (d[u] < l && l - d[u] < w && w - l + d[u] + d[v] > l) ans++;
    if (d[v] < l && l - d[v] < w && w - l + d[v] + d[u] > l) ans++;
    if (d[v] < l && d[u] < l && d[u] + d[v] + w == 2 * l) ans++;
  }
  return ans;
}
int main() {
  int n, m, s;
  scanf("%d%d%d", &n, &m, &s);
  s--;
  int t1, t2, t3;
  vector<vector<pair<int, int> > > g(n);
  for (int i = 0; i < m; ++i) {
    scanf("%d%d%d", &t1, &t2, &t3);
    t1--;
    t2--;
    edges.push_back(edge(t1, t2, t3));
    g[t1].push_back(make_pair(t2, t3));
    g[t2].push_back(make_pair(t1, t3));
  }
  vector<int> d = Dijkstra(g, s, n);
  int l;
  scanf("%d", &l);
  printf("%d\n", getAnswer(d, l, n, m));
  return 0;
}
