Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <algorithm>
- #include <cstring>
- #include <ctime>
- #include <iostream>
- #include <map>
- #include <set>
- #include <stack>
- #include <string>
- #include <unordered_map>
- #include <unordered_set>
- #include <vector>
- using namespace std;
- #ifdef __APPLE__
- #define eprintf(...) fprintf(stderr, __VA_ARGS__)
- #else
- #define eprintf(...)
- #endif
- const int N = (int)1e5 + 123;
- const int MOD = (int)1e9 + 7;
- const int inf = (int)5e8;
- const long long infll = (long long)2e18;
- struct Edge {
- int u;
- int v;
- long long t;
- int id;
- Edge() = default;
- Edge(int u, int v, long long t, int id) : u(u), v(v), t(t), id(id) {}
- };
- vector<pair<long long, long long>> block[N];
- vector<int> g[N];
- Edge edges[N];
- long long h2 = 100500;
- long long h1 = 100;
- long long h3 = 1;
- long long my_ceil(long long tnow, long long f1, long long t) {
- if (h1 + tnow - f1 > h2 * h1) return h2 * t;
- if (((tnow - f1) * t) % h1 == 0) return t + ((tnow - f1) * t) / h1;
- else return t + ((tnow - f1) * t) / h1 + h3;
- }
- void solve() {
- int n, m;
- scanf("%d %d", &n, &m);
- for (int i = 0; i < m; ++i) {
- int u, v, t;
- scanf("%d %d %d", &u, &v, &t);
- --u;
- --v;
- edges[i] = Edge(u, v, t, i);
- g[u].push_back(i);
- g[v].push_back(i);
- }
- int k;
- scanf("%d", &k);
- for (int i = 0; i < k; ++i) {
- int id;
- long long s, f;
- scanf("%d %lld %lld", &id, &s, &f);
- --id;
- block[id].push_back({s, f});
- }
- for (int i = 0; i < m; ++i) {
- block[i].push_back({-1, 0});
- block[i].push_back({infll, infll + 1});
- sort(block[i].begin(), block[i].end());
- }
- set<pair<long long, int>> que = {{0LL, 0}};
- vector<long long> dist(n, infll);
- dist[0] = 0;
- while (que.size() > 0) {
- int u = que.begin()->second;
- que.erase(que.begin());
- for (auto to : g[u]) {
- long long time = dist[u];
- auto edge = edges[to];
- int v = edge.v;
- if (u == v) {
- v = edge.u;
- }
- auto it = upper_bound(block[edge.id].begin(), block[edge.id].end(),
- make_pair(time, 0LL));
- auto prev = it - 1;
- while (it != block[edge.id].end()) {
- long long edge_len = my_ceil(time, prev->second, edge.t);
- long long begin = it->first;
- long long end = it->second;
- if (time + edge_len <= begin) {
- if (dist[v] > time + edge_len) {
- que.erase({dist[v], v});
- dist[v] = time + edge_len;
- que.insert({dist[v], v});
- }
- break;
- }
- time = end;
- ++it;
- ++prev;
- }
- }
- }
- if (dist[n - 1] >= infll) throw;
- printf("%lld\n", dist[n - 1]);
- }
- int main() {
- #ifdef __APPLE__
- freopen("input.txt", "r", stdin);
- freopen("output.txt", "w", stdout);
- #endif
- int t = 1;
- while (t--) {
- solve();
- }
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement