제출 #631219

#제출 시각아이디문제언어결과실행 시간메모리
631219qwerasdfzxcl던전 (IOI21_dungeons)C++17
100 / 100
3376 ms1499704 KiB
#include "dungeons.h" #include <bits/stdc++.h> using namespace std; typedef long long ll; constexpr int S = 4, T = 12, L = 24, L2 = 20, MX = 400002, INF = 1e9+100; struct Node{ int s, c, val; Node(){} Node(int _s, int _c, int _v): s(_s), c(_c), val(_v) {} Node operator + (const Node &S) const{ assert((ll)c + S.c <= INF); return Node(S.s, c+S.c, min(val, S.val-c)); } }sp1[L][T][MX]; pair<int, ll> sp2[L2][MX]; int n; pair<int, ll> operator + (const pair<int, ll> &a, const pair<int, ll> &b){return {b.first, a.second+b.second};} vector<int> is, ip, iw, il; void init(int N, std::vector<int> s, std::vector<int> p, std::vector<int> w, std::vector<int> l) { is = s, ip = p, iw = w, il = l; n = N; for (int i=0;i<L;i++){ for (int v=0;v<n;v++){ if (s[v]<=(1<<i)) sp1[i][0][v] = Node(w[v], s[v], INF); else sp1[i][0][v] = Node(l[v], p[v], s[v]); } for (int j=1;j<T;j++){ for (int v=0;v<n;v++){ sp1[i][j][v] = sp1[i][j-1][v]; if (sp1[i][j-1][v].s==n || sp1[i][j-1][v].c >= (1<<i)) continue; for (int t=0;t<S-1;t++){ int cur = sp1[i][j][v].s; sp1[i][j][v] = sp1[i][j][v] + sp1[i][j-1][cur]; if (sp1[i][j][v].s==n || sp1[i][j][v].c >= (1<<i)) break; } } } } for (int v=0;v<n;v++) sp2[0][v] = {w[v], s[v]}; for (int j=1;j<L2;j++){ for (int v=0;v<n;v++){ sp2[j][v] = sp2[j-1][v]; if (sp2[j][v].first==n) continue; sp2[j][v] = sp2[j][v] + sp2[j-1][sp2[j-1][v].first]; } } } long long simulate(int pos, int mp0) { ll mp = mp0; for (int i=0;i<L;i++){ if (mp >= (1<<(i+1))) continue; Node cur(pos, 0, INF); for (int j=T-1;j>=0;j--){ int loop = 0; while(true){ assert(++loop <= S+2); Node nxt = cur + sp1[i][j][cur.s]; if (nxt.s == n || nxt.c >= ((1<<(i+1))-mp) || mp >= nxt.val) break; cur = nxt; } } pos = cur.s; mp += cur.c; assert(pos!=n && mp < (1<<(i+1))); if (mp >= is[pos]){mp += is[pos]; pos = iw[pos];} else {mp += ip[pos]; pos = il[pos];} if (pos==n) return mp; assert(mp >= (1<<(i+1))); } for (int j=L2-1;j>=0;j--) if (sp2[j][pos].first!=n){ mp += sp2[j][pos].second; pos = sp2[j][pos].first; } assert(pos!=n); assert(sp2[0][pos].first==n); return mp + sp2[0][pos].second; }
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...