首页 > 其他分享 >[题解] AT_dp_w Intervals

[题解] AT_dp_w Intervals

时间:2023-11-11 11:14:19浏览次数:38  
标签:le leftarrow int 题解 sum Intervals aligned ll dp

Intervals

有 \(m\) 条形如 \((l, r, a)\) 的限制,表示如果 \(s_{[l, r]}\) 中有 1 就会有 \(a\) 的价值。
你要求长度为 \(n\) 的 01 串的价值的最大值。
\(n, m \le 2 \times 10^5\)。

将每个限制挂到右端点上,在右端点处计算贡献。然后我们就只关心最后一个 1 出现的位置了。

所以设计 dp 状态为 \(f_{i, j}\) 表示考虑了前 \(i\) 位,最后一个 1 的位置为 \(j\) 的方案数。

转移就分类讨论一下这一位填 1 还是填 0:

\[ \begin{aligned} &f_{i, j} \leftarrow f_{i - 1, j} + \sum_{l_k \le j, r_k = i} a_k \\ &f_{i, i} \leftarrow \max_{j \in [0, i - 1]} f_{i - 1, j} + \sum_{l_k \le j, r_k = i} a_k \end{aligned} \]

第一个转移是第 \(i\) 位填 1 的,第二个是第 \(i\) 位填 0 的。

但这个是 \(O(n^2)\) 的,还要继续优化。

首先把第一维滚掉,变成:

\[ \begin{aligned} &f_{j} \leftarrow f_{j} + \sum_{l_k \le j, r_k = i} a_k \\ &f_{i} \leftarrow \max_{j \in [0, i - 1]} f_{j} + \sum_{l_k \le j, r_k = i} a_k \end{aligned} \]

然后就可以发现这个可以扔到线段树上变成区间加,区间 \(\max\)。

时间复杂度 \(O(n \log n)\)。

constexpr int MAXN = 2e5 + 9;
int n, m;
vector<pair<int, int> > vec[MAXN];

struct Node {
	ll sum, mx, add;
	
	Node(): sum(0), mx(0), add(0) { return; }
	Node(ll _s, ll _m, ll _a): sum(_s), mx(_m), add(_a) { return; }
} sgt[MAXN << 2];

void Push_Tag(int p, int len, ll k) {
	sgt[p].sum += k * len;
	sgt[p].mx += k;
	sgt[p].add += k;
	return;
}
void Push_Up(int p) {
	sgt[p].sum = sgt[p << 1].sum + sgt[p << 1 | 1].sum;
	sgt[p].mx = max(sgt[p << 1].mx, sgt[p << 1 | 1].mx);
	return;
}
void Push_Down(int p, int L, int R) {
	if (sgt[p].add) {
		int Mid = L + R >> 1;
		Push_Tag(p << 1, Mid - L + 1, sgt[p].add);
		Push_Tag(p << 1 | 1, R - Mid, sgt[p].add);
		sgt[p].add = 0;
	}
	return;
}
void Update(int l, int r, ll k, int L = 0, int R = n, int p = 1) {
	if (l <= L && R <= r) return Push_Tag(p, R - L + 1, k);
	Push_Down(p, L, R); int Mid = L + R >> 1;
	if (l <= Mid) Update(l, r, k, L, Mid, p << 1);
	if (Mid < r) Update(l, r, k, Mid + 1, R, p << 1 | 1);
	Push_Up(p); return;
}

void slv() {
	n = Read<int>(), m = Read<int>();
	for (int i = 1; i <= m; i ++) {
		int l = Read<int>(), r = Read<int>(), a = Read<int>();
		vec[r].emplace_back(l, a);
	}
	for (int r = 1; r <= n; r ++) {
		Update(r, r, sgt[1].mx);
		for (auto [l, a] : vec[r]) Update(l, r, a);
	}
	Write(sgt[1].mx, '\n');
	return;
}

标签:le,leftarrow,int,题解,sum,Intervals,aligned,ll,dp
From: https://www.cnblogs.com/definieren/p/17825664.html

相关文章

  • 转 问题解决:记录一次Linux服务器根目录突然爆满
    一般跟目录满了,可以重点关注/var这个目录 一、出问题了过了个双休来到公司,同时发现Linux终端的服务器状态中根目录空间直接爆满100%,周五走之前根目录仅仅使用了59%,同时项目服务的后台不停的有日志打印,而且测试的小伙伴说系统登录不上去了。下面记录一下个人排查并解决这个问题......
  • 【小沐学前端】Windows下搭建WordPress(一、相关工具下载)
    1、简介WordPress是基于PHP和MySQL的免费开源内容管理系统(CMS)。它是全球使用最广泛的CMS软件,截至2019年5月,它为排名前1000万个网站中提供了超过30%的支持,并拥有在使用CMS构建的所有网站中,估计有60%的市场份额。1.1Nginxnginx[enginex]是一个HTTP和反向代理服务器,邮件代理......
  • To_Heart—总结——连通块 dp(抑或 连续块 dp)
    简介有一类问题,他们需要计算满足在序列上插入给定顺序的元素,其贡献/限制只与两旁的元素有关,但元素插入的位置是不一定的,所以会有代价的最值和方案数的统计。而对于这类问题,我们其实可以不关心每一次插入的具体位置在哪里,而只关注他的相对位置(比如在某个数左边、在某个数左边且与......
  • CF1485F Copy or Prefix Sum 题解
    思路考虑\(a_i\)要么是\(b_i\)要么是\(b_i-s\)。考虑\(s\)代表着什么。它是\(a\)的前缀和。那么必然是往前一段\(b\)的和。因为每个\(b\)代表着要么是这一位的\(a\)或者前面所有的\(a\)。考虑设\(f_i\)为这个位置填\(b_i\)的方案数。\(g_i\)为这个......
  • [POI2011] SMI-Garbage 题解
    题目链接显然,对于初始颜色与目标颜色不同的边,我们需要走过奇数次;对于初始颜色与目标颜色相同的边,我们需要走过偶数次。对于只有偶数边的情况,这种情况下不走就行;对于只有奇数边;可以理解为每条边只能经过一次,就是欧拉路径问题,并且考虑这题的特殊性质,如果一个图是由若干个简单环构......
  • CSP-S2019 江西 题解
    为什么有\(5\)道题?[CSP-S2019江西]和积和简单化一下式子:\[(n+1)\times\sumA_i\timesB_i-(\sumA_i)\times(\sumB_i)\]其中\(A,B\)都是前缀和。[CSP-S2019江西]网格图naive的kruskal是很naive的,所以需要一点简单的优化。考虑其本质过程就是按照......
  • CF1485E Move and Swap 题解
    不要什么脑子的带\(log\)做法。思路考虑\(dp_{i,j}\)表示红点到\(i\),蓝点到\(j\)的最大权值。那么有:\[dp_{i,j}=\max(dp_{fa_i,pre},dp_{fa_j,pre})+|a_i-a_j|\]其中\(pre\)是任意一个上一层节点。发现第二维没有用。可以优化:\[dp_i=\max(dp_{fa_i}+\max(|a_i-a_......
  • APISIX源码安装问题解决
    官网手册的安装语句:curlhttps://raw.githubusercontent.com/apache/apisix/master/utils/install-dependencies.sh-sL|bash-执行install-dependencies.sh报如下错误:Transactioncheckerror:file/usr/share/gcc-4.8.2/python/libstdcxx/v6/printers.pyfrominstal......
  • 苏格拉底问答、实践过程截图、遇到问题解决问题截图,代码链接
    #include<stdio.h>#include<stdlib.h>#include<string.h>#include<unistd.h>#include<signal.h>#include<setjmp.h> //foralongjumpjmp_bufenv;//forsavinglonjmpenviromentintcount=0;voidhandler(intsig,......
  • CSP-2019-S 题解
    做了这套题,如果是让现在的我当时去考的话应该一共可以有450分,格雷码,括号树,树的重心都可以做,树上的数可以有10分,Emiya至少可以有76分,划分也可以有64分。看OIerDB上可以有166名的好成绩。我的代码合集:洛谷/云剪贴板[CSP-S2019]格雷码首先是格雷码有一个很好的生......