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>
#define nl '\n'
#ifdef LOCAL
#include "template/debug.hpp"
#else
#define dbg(...) ;
#define timer(...) ;
#endif
template <typename T, typename F = std::plus<T>>
struct IterativeSegmentTree {
int n;
std::vector<T> tree;
IterativeSegmentTree() {}
IterativeSegmentTree(int _n) { init(_n); }
void init(int _n) {
n = _n;
tree.assign(2 * n, T());
}
template <typename Vec>
void build(const Vec& v) {
init(v.size());
for (int i = n; i < 2 * n; i++) tree[i] = T::from_value(v[i - n]);
for (int i = n - 1; i > 0; i--)
tree[i] = F()(tree[i << 1], tree[i << 1 | 1]);
}
template <typename Vec>
IterativeSegmentTree(const Vec& a) {
build(a);
}
void modify(int p, const T& v) {
for (tree[p += n] = v; p >>= 1;) {
tree[p] = F()(tree[p << 1], tree[p << 1 | 1]);
}
}
T query(int l, int r) {
T resl = T(), resr = T();
for (l += n, r += n; l < r; l >>= 1, r >>= 1) {
if (l & 1) resl = F()(resl, tree[l++]);
if (r & 1) resr = F()(tree[--r], resr);
}
return F()(resl, resr);
}
T get(int i) const {
return tree[i + n];
}
};
struct Info {
int64_t v = -1e9;
Info() {}
Info(int64_t x) : v(x) {}
static Info from_value(int64_t x) {
return {x};
}
friend Info operator+(const Info& l, const Info& r) {
return {std::max(l.v, r.v)};
}
};
signed main() {
std::ios::sync_with_stdio(false);
std::cin.tie(nullptr);
int n, d;
std::cin >> n >> d;
std::vector<int> a(n);
for (int i = 0; i < n; i++) {
std::cin >> a[i];
}
int sz;
{
auto v = a;
std::sort(v.begin(), v.end());
v.erase(std::unique(v.begin(), v.end()), v.end());
for (int i = 0; i < n; i++) {
a[i] = std::lower_bound(v.begin(), v.end(), a[i]) - v.begin();
}
sz = v.size();
}
IterativeSegmentTree<Info> tree(sz);
std::vector<std::deque<int>> dq(sz);
std::vector<int> dp(n);
auto add = [&](int x, int v) {
while (dq[x].size() && dp[dq[x].back()] < dp[v]) {
dq[x].pop_back();
}
dq[x].push_back(v);
tree.modify(x, dp[dq[x].front()]);
};
auto rem = [&](int x, int v) {
while (dq[x].size() && dq[x].front() <= v) {
dq[x].pop_front();
}
tree.modify(x, dq[x].size() ? dp[dq[x].front()] : -1e9);
};
for (int i = 0; i < n; i++) {
dp[i] = 1;
int cand = tree.query(0, a[i]).v + 1;
dp[i] = std::max(dp[i], cand);
add(a[i], i);
if (i - d >= 0) {
rem(a[i - d], i - d);
}
}
std::cout << *std::max_element(dp.begin(), dp.end()) << nl;
}
# | 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... |