#include using namespace std; typedef long long ll; typedef pair P; typedef tuple State; // dist, building, floor const ll INF = 1LL << 60; map vmap; map> nxt; // building floor-> next floor vector F[200000]; ll dist[500000]; int main(){ cin.tie(0); ios::sync_with_stdio(false); #ifdef LOCAL std::ifstream in("in"); std::cin.rdbuf(in.rdbuf()); #endif int N, M, K, S, T; cin >> N >> M >> K >> S >> T; F[0].push_back(S); F[N - 1].push_back(T); for(int i = 0; i < M; i++){ int a, b, c; cin >> a >> b >> c; a--; F[a].push_back(b); F[a + 1].push_back(c); nxt[{a, b}].push_back(c); } int V = 0; for(int i = 0; i < N; i++){ sort(F[i].begin(), F[i].end()); F[i].erase(unique(F[i].begin(), F[i].end()), F[i].end()); for(auto f : F[i]){ vmap[{i, f}] = V++; } } P start = { 0, S }; P goal = { N - 1, T }; if(vmap.count(start) == 0) vmap[start] = V++; if(vmap.count(goal) == 0) vmap[goal] = V++; fill((ll*)begin(dist), (ll*)end(dist), INF); dist[vmap[start]] = 0; priority_queue, greater> q; q.push({ 0, 0, S }); while(q.size()){ ll d; int b, f; tie(d, b, f) = q.top(); q.pop(); if(nxt.count({ b, f })){ for(auto nc : nxt[{b, f}]){ State ns = { d, b + 1, nc }; if(dist[vmap[{ b + 1, nc }]] > d){ dist[vmap[{ b + 1, nc }]] = d; q.push(ns); } } } int idx = lower_bound(F[b].begin(), F[b].end(), f) - F[b].begin(); for(int i = idx - 1; i <= idx + 1; i += 2){ if(i < 0 || F[b].size() <= i) continue; ll nd = d + abs(f - F[b][i]); State ns = { nd, b, F[b][i] }; if(dist[vmap[{ b, F[b][i] }]] > nd){ dist[vmap[{ b, F[b][i] }]] = nd; q.push(ns); } } } if(dist[vmap[goal]] == INF) cout << -1 << endl; else cout << dist[vmap[goal]] << endl; }