2 条题解
-
0
#include <queue> #include <vector> #include <cmath> using namespace std; typedef long long ll; const ll INF = 1e18; int N, M; ll a[100005]; ll val[400005]; int L[400005], R[400005]; bool del[400005]; int main() { ios_base::sync_with_stdio(false); cin.tie(NULL); cin >> N >> M; for (int i = 1; i <= N; i++) { cin >> a[i]; } // 压缩:合并连续同号数为"块" vector<ll> blocks; ll cur = 0; bool has = false; for (int i = 1; i <= N; i++) { if (a[i] == 0) continue; if (!has) { cur = a[i]; has = true; } else if ((cur > 0) == (a[i] > 0)) { cur += a[i]; } else { blocks.push_back(cur); cur = a[i]; } } if (has) blocks.push_back(cur); // 去掉首尾的负数块 while (!blocks.empty() && blocks.front() <= 0) blocks.erase(blocks.begin()); while (!blocks.empty() && blocks.back() <= 0) blocks.pop_back(); if (blocks.empty()) { cout << 0 << endl; return 0; } // 统计正数块数量和总和 int K = 0; ll posSum = 0; for (size_t i = 0; i < blocks.size(); i++) { if (blocks[i] > 0) { K++; posSum += blocks[i]; } } if (K <= M) { cout << posSum << endl; return 0; } // 建双向链表 + 哨兵节点(0和n+1) int n = blocks.size(); priority_queue<pair<ll, int>, vector<pair<ll, int>>, greater<pair<ll, int>> > pq; val[0] = INF; val[n + 1] = INF; for (int i = 1; i <= n; i++) { val[i] = abs(blocks[i - 1]); del[i] = false; L[i] = i - 1; R[i] = i + 1; pq.push(make_pair(val[i], i)); } del[0] = false; del[n + 1] = false; R[0] = 1; L[n + 1] = n; // 反悔贪心:选K-M个代价最小的操作 int nextNode = n + 2; ll totalCost = 0; int ops = K - M; for (int t = 0; t < ops; t++) { while (!pq.empty() && del[pq.top().second]) { pq.pop(); } if (pq.empty()) break; pair<ll, int> top = pq.top(); pq.pop(); ll v = top.first; int i = top.second; totalCost += v; int l = L[i]; int r = R[i]; del[l] = true; del[i] = true; del[r] = true; int ll = L[l]; int rr = R[r]; // 合并节点:若以后选它 = 反悔选i,改选l和r int merged = nextNode++; val[merged] = val[l] + val[r] - v; del[merged] = false; L[merged] = ll; R[merged] = rr; R[ll] = merged; L[rr] = merged; pq.push(make_pair(val[merged], merged)); } cout << posSum - totalCost << endl; return 0; }
信息
- ID
- 74
- 时间
- 1000ms
- 内存
- 128MiB
- 难度
- 6
- 标签
- 递交数
- 72
- 已通过
- 20
- 上传者