This submission is migrated from previous version of oj.uz, which used different machine for grading. This submission may have different result if resubmitted.
#include <bits/stdc++.h>
#include "jumps.h"
using namespace std;
#define all(x) x.begin(), x.end()
#define ar array
#define pb push_back
#define ln '\n'
//#define int long long
using i64 = long long;
template <class F, class _S>
bool chmin(F &u, const _S &v){
bool flag = false;
if ( u > v ){
u = v; flag |= true;
}
return flag;
}
template <class F, class _S>
bool chmax(F &u, const _S &v){
bool flag = false;
if ( u < v ){
u = v; flag |= true;
}
return flag;
}
const int N = 2e5 + 1;
vector <int> L, R, H;
vector <vector<int>> up(20), _up(20);
int n;
struct SegTree{
int T[N * 4], id[N * 4];
SegTree(){
for ( int i = 0; i < N * 4; i++ ){
T[i] = 0;
}
}
void upd(int v, int l, int r, int pos, int val){
if ( l == r ){
T[v] = val;
id[v] = l;
return;
}
int md = (l + r) >> 1;
if ( pos > md ){
upd(v * 2 + 1, md + 1, r, pos, val);
} else{
upd(v * 2, l, md, pos, val);
}
T[v] = max(T[v * 2], T[v * 2 + 1]);
if ( T[v] == T[v * 2] ){
id[v] = id[v * 2];
} else id[v] = id[v * 2 + 1];
};
void upd(int pos, int val){
upd(1, 0, n - 1, pos, val);
}
pair <int,int> get(int v, int l, int r, int tl, int tr){
pair <int,int> ret;
ret = {-1, -1};
if ( l > tr or r < tl ){
return ret;
}
if ( tl <= l && tr >= r ){
return {T[v], id[v]};
}
int md = (l + r) >> 1;
return max(get(v * 2, l, md, tl, tr), get(v * 2 + 1, md + 1, r, tl, tr));
}
int get(int l, int r){
return get(1, 0, n - 1, l, r).second;
}
} seg;
int f(int u, int v){
int ret = 0;
for ( int i = 19; i >= 0; i-- ){
if ( H[up[i][u]] <= H[v] ){
ret += 1 << i;
u = up[i][u];
}
}
for ( int i = 19; i >= 0; i-- ){
if ( H[_up[i][u]] <= H[v] ){
ret += 1 << i;
u = _up[i][u];
}
}
if ( H[u] != H[v] ) ret = -1;
return ret;
}
void init(int N, std::vector<int> H_) {
n = N; H = H_;
L.resize(n), R.resize(n);
H.pb(n + 5);
for ( int i = 0; i < 20; i++ ){
up[i].resize(n + 1, n);
_up[i].resize(n + 1, n);
}
{
stack <int> stk;
stk.push(-1);
for ( int i = 0; i < n; i++ ){
while ( stk.size() > 1 && H[stk.top()] <= H[i] ){
stk.pop();
} L[i] = stk.top();
stk.push(i);
}
while ( stk.size() > 1 ) stk.pop();
for ( int i = n - 1; i >= 0; i-- ){
while ( stk.size() > 1 && H[stk.top()] <= H[i] ){
stk.pop();
} R[i] = stk.top();
stk.push(i);
}
}
for ( int i = 0; i < n; i++ ){
if ( L[i] == -1 && R[i] == -1 ){
continue;
}
if ( L[i] == -1 || (R[i] != -1 && H[L[i]] < H[R[i]]) ){
up[0][i] = R[i];
} else up[0][i] = L[i];
}
for ( int i = 0; i < n; i++ ){
seg.upd(i, H[i]);
if ( R[i] != -1 ){
_up[0][i] = R[i];
}
}
for ( int i = 1; i < 20; i++ ){
for ( int j = 0; j <= n; j++ ){
up[i][j] = up[i - 1][up[i - 1][j]];
_up[i][j] = _up[i - 1][_up[i - 1][j]];
}
}
}
int minimum_jumps(int A, int B, int C, int D) {
int l = A, r = B, v = seg.get(C, D);
while ( l < r ){
int md = (l + r) >> 1;
if ( H[seg.get(md, B)] < H[v] ){
r = md;
} else l = md + 1;
} A = l;
int u = seg.get(A, B), opt = f(u, v);
auto ok = [&](int u){
for ( int i = 19; i >= 0; i-- ){
if ( _up[i][u] <= D ){
u = _up[i][u];
}
}
return C <= u && u <= D;
};
l = A, r = B;
while ( l < r ){
int md = (l + r) >> 1;
if ( ok(seg.get(md, B)) ) r = md;
else l = md + 1;
}
u = seg.get(l, B);
int q = 0;
for ( int i = 19; i >= 0; i-- ){
if ( _up[i][u] < C ){
u = _up[i][u];
q += 1 << i;
}
}
u = _up[0][u];
if ( u <= D ){
if ( opt == -1 || opt > q + 1 ){
opt = q + 1;
}
}
return opt;
}
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |