P2048 [NOI2010] 超级钢琴
其实这道题在我刚学 oi 两个月 (2023.3) 就见过了
当时是作为 st 表的一个例题出现的, 我学 st 表就已经学得迷迷糊糊的了, 更别说这题了哈哈
所以这是第二次见到他, 必须写了(这一次他是作为 NOIP 模拟赛的一个部分分做法出现的)
思路
不错的限制:每个和弦都是连续的
所以可以考虑一个基于起点位置的贪心
按照常规的思路
然后把他们丢进优先队列, 每次取堆顶, 把
但是
这个序列不是单调的, 因为中间有一些负数
这就意味着距离
所以上述做法只能用于一个削弱版的本题
该如何改进呢
其实并不难, 但是我一开始没想出来
设
这样, 每次取完堆顶后,
这一步可以用 st 表实现, 是
总时间复杂度
代码
#include <bits/stdc++.h> #define int long long // #pragma GCC optimize(2) using namespace std; const int N = 5e5 + 10, Base = 191; int n, k, l, r; int a[N]; int st[20][N], ps[20][N]; void Init(){ for(int i = 1; i < 20; i++){ for(int j = 0; j + (1 << i) - 1 <= n; j++){ if(st[i - 1][j] > st[i - 1][j + (1 << (i - 1))]){ st[i][j] = st[i - 1][j]; ps[i][j] = ps[i - 1][j]; }else{ st[i][j] = st[i - 1][j + (1 << (i - 1))]; ps[i][j] = ps[i - 1][j + (1 << (i - 1))]; } } } } struct Ret{ int maxi, maxid; }; Ret Query(int l, int r){ int k = __lg(r - l + 1); Ret ret = {0, 0}; if(st[k][l] > st[k][r - (1 << k) + 1]){ ret.maxi = st[k][l]; ret.maxid = ps[k][l]; }else{ ret.maxi = st[k][r - (1 << k) + 1]; ret.maxid = ps[k][r - (1 << k) + 1]; } return ret; } struct Node{ int idx, l, r, mid, v; bool operator < (const Node &p)const{ return v < p.v; } }tp; priority_queue <Node> q; signed main(){ // freopen("1.in", "r", stdin); cin >> n >> k >> l >> r; for(int i = 1; i <= n; i++){ cin >> a[i]; st[0][i] = st[0][i - 1] + a[i]; ps[0][i] = i; } Init(); for(int i = 1; i + l - 1 <= n; i++){ int ll = i + l - 1, rr = min(i + r - 1, n); auto ret = Query(ll, rr); q.push({i, ll, rr, ret.maxid, ret.maxi - st[0][i - 1]}); } int sum = 0; for(int i = 1; i <= k; i++){ tp = q.top(); q.pop(); sum += tp.v; if(tp.mid - 1 >= tp.l){ int ll = tp.l, rr = tp.mid - 1; auto ret = Query(ll, rr); q.push({tp.idx, ll, rr, ret.maxid, ret.maxi - st[0][tp.idx - 1]}); } if(tp.mid + 1 <= tp.r){ int ll = tp.mid + 1, rr = tp.r; auto ret = Query(ll, rr); q.push({tp.idx, ll, rr, ret.maxid, ret.maxi - st[0][tp.idx - 1]}); } } cout << sum << "\n"; }
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 按钮权限的设计及实现
· 25岁的心里话