#include <cstdio> #include <vector> #include <algorithm> #define MAX_N 300100 using namespace std; int n, q, k; long long pref[MAX_N]; long long wyn[MAX_N]; long long dp[MAX_N]; void divConq(int l, int r, vector<pair<int, pair<int, int>>> zap) { if (zap.empty()) { return; } vector<pair<int, pair<int, int> > > left, right, here; int mid = (l + r) >> 1; for (auto a : zap) { if (a.second.second <= mid) { left.push_back(a); } else if (a.second.first > mid) { right.push_back(a); } else { here.push_back(a); } } divConq(l, mid, left); divConq(mid + 1, r, right); if (here.empty()) { return; } int lp = r; int rp = l; for (auto a : here) { lp = min(lp, a.second.first); rp = max(rp, a.second.second); } for (int i = mid + 1; i <= min(mid + k - 1, rp); i++) { dp[i] = 0; } for (int i = mid; i >= max(mid - k + 1, lp); i--) { dp[i] = 0; } for (int offset = 0; offset <= k; offset++) { int origin = mid + offset; if (origin + k - 1 <= rp) { dp[origin + k - 1] = 0; } if (origin + k <= rp) { dp[origin + k] = max(0ll, pref[origin + k] - pref[origin]); } for (int i = origin + k + 1; i <= rp; i++) { dp[i] = max(dp[i - 1], dp[i - k] + pref[i] - pref[i - k]); } if (origin - k + 1 >= lp) { dp[origin - k + 1] = max(0ll, pref[origin] - pref[origin - k]); } for (int i = origin - k; i >= lp; i--) { dp[i] = max(dp[i + 1], dp[i + k] + pref[i + k - 1] - pref[i - 1]); } for (auto a : here) { if (a.second.first <= origin && a.second.second > origin) { wyn[a.first] = max(wyn[a.first], dp[a.second.first] + dp[a.second.second]); } else if (a.second.second == origin) { wyn[a.first] = max(wyn[a.first], dp[a.second.first]); } } } } int main() { scanf("%d%d%d", &n, &k, &q); for (int i = 1; i <= n; i++) { scanf("%lld", &pref[i]); pref[i] += pref[i - 1]; } vector<pair<int, pair<int, int>>> v; for (int i = 0; i < q; i++) { int a, b; scanf("%d%d", &a, &b); if (b - a + 1 < k) wyn[i] = 0; else if (b - a + 1 == k) wyn[i] = max(0ll, pref[b] - pref[a - 1]); else v.emplace_back(i, make_pair(a, b)); } divConq(1, n, v); for (int i = 0; i < q; i++) { printf("%lld\n", wyn[i]); } }
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 | #include <cstdio> #include <vector> #include <algorithm> #define MAX_N 300100 using namespace std; int n, q, k; long long pref[MAX_N]; long long wyn[MAX_N]; long long dp[MAX_N]; void divConq(int l, int r, vector<pair<int, pair<int, int>>> zap) { if (zap.empty()) { return; } vector<pair<int, pair<int, int> > > left, right, here; int mid = (l + r) >> 1; for (auto a : zap) { if (a.second.second <= mid) { left.push_back(a); } else if (a.second.first > mid) { right.push_back(a); } else { here.push_back(a); } } divConq(l, mid, left); divConq(mid + 1, r, right); if (here.empty()) { return; } int lp = r; int rp = l; for (auto a : here) { lp = min(lp, a.second.first); rp = max(rp, a.second.second); } for (int i = mid + 1; i <= min(mid + k - 1, rp); i++) { dp[i] = 0; } for (int i = mid; i >= max(mid - k + 1, lp); i--) { dp[i] = 0; } for (int offset = 0; offset <= k; offset++) { int origin = mid + offset; if (origin + k - 1 <= rp) { dp[origin + k - 1] = 0; } if (origin + k <= rp) { dp[origin + k] = max(0ll, pref[origin + k] - pref[origin]); } for (int i = origin + k + 1; i <= rp; i++) { dp[i] = max(dp[i - 1], dp[i - k] + pref[i] - pref[i - k]); } if (origin - k + 1 >= lp) { dp[origin - k + 1] = max(0ll, pref[origin] - pref[origin - k]); } for (int i = origin - k; i >= lp; i--) { dp[i] = max(dp[i + 1], dp[i + k] + pref[i + k - 1] - pref[i - 1]); } for (auto a : here) { if (a.second.first <= origin && a.second.second > origin) { wyn[a.first] = max(wyn[a.first], dp[a.second.first] + dp[a.second.second]); } else if (a.second.second == origin) { wyn[a.first] = max(wyn[a.first], dp[a.second.first]); } } } } int main() { scanf("%d%d%d", &n, &k, &q); for (int i = 1; i <= n; i++) { scanf("%lld", &pref[i]); pref[i] += pref[i - 1]; } vector<pair<int, pair<int, int>>> v; for (int i = 0; i < q; i++) { int a, b; scanf("%d%d", &a, &b); if (b - a + 1 < k) wyn[i] = 0; else if (b - a + 1 == k) wyn[i] = max(0ll, pref[b] - pref[a - 1]); else v.emplace_back(i, make_pair(a, b)); } divConq(1, n, v); for (int i = 0; i < q; i++) { printf("%lld\n", wyn[i]); } } |