差分约束进阶
三步法求解差分约束
- 找不等式关系,确定是最短路还是最长路
- 将不等式转换为熟悉的式子建边
- 跑最长路或最短路
T712556 AT_abc216_g [ABC216G] 01Sequence
找到一个长度为 \(n\) 的 \(01\) 数列,是的满足 \(m\) 个条件 \(L_i\) 到 \(R_i\) 至少有 \(X_i\) 个 \(1\) , 且1的数量最小,输出这个数列, 一定有解
先找不等式关系, 令 \(s_i\) 表示前 \(i\) 个数列里有多少个 \(1\),就有一下两个不等关系
第二个好理解,用\(s_i - s_{i-1}\) 表示 \(i\) 号位的 \(1\) 个数, 因为只能选择放和不放 \(1\) 所以在 有这个关系
补充
\(a \leq b+c\) , 建边 \((b, a, c)\) ,跑最短路
\(a \ge b+c\) , 建边 \((b, a, c)\) , 跑最长路
这题类似之前的 种树 要让数量尽可能少, 所以也按最长路来, 把不等式转换成 \(a \ge b +c\) 的形式建边于是要建
这些边
\(dis_{i+1} - dis_i\) 就是第 \(i\) 个位置的答案
发现不对, \(n \leq 2e5\), \(spfa\) 不行,想到 \(Dijkstra\)
边权有正有负,怎么办?
把统计 \(1\) 的数量 改成统计 \(0\) 的数量跑最短路
最短路找至多,最长路找至少,因为要让 \(1\) 的数量至少, 随意就是让 \(0\) 的数量至多,所以跑最短路
重新来改不等式, 令\(s_i\) 表示 \(0\) 数量的前缀和
\([l,r]\) 的 \(0\) 个数 : \(s_r - s_{l-1}\)
所以
\([l,r]\) 的 \(1\) 个数 : \((r-l+1) - (s_r - s_{l-1})\)
所以按照限制 \(1\) 个数 \(\ge\) \(x\)
转成熟悉的格式
所以建立\((l-1,r,(r-l+1)-x)\) 这条边
另外的那个式子可以变成
所以建 \((i-1,i,1) ,\;(i,i-1,0)\) 两条边
边权都一定是正数, 从 \(0\) 出发跑 \(Dijkstra\), 每一个位置的 \(0\) 的个数是 $$dis_i - dis_{i-1}$$
个数是\(1\)输出\(0\),是\(0\)输出\(1\)
P5590 赛车游戏
任意路径不一定是最短路径,等长 $\Rightarrow $ 等长的所有路径都是最短路
要满足上面条件,那么最短路是对于每一条边都满足条件 \(dis_u + w = dis_v\) $\Rightarrow $ \(w = dis_v - dis_u\)
而 \(1 \leq w \leq 9\)
所以找到了不等关系 !!!
\(1 \leq dis_v - dis_u \leq 9\)
转成
- \(dis_u \leq dis_v - 1\)
- \(dis_v \leq dis_u + 9\)
建边 - ① \((v, u, -1)\)
- ② \((u,v,9)\)
还有一些边不在 \(1\) 到 \(n\) 的路径上, 这些边想填什么填什么, 不要建边, 它对最短路没有影响, 不然会出现一个单独的负环在外面,导致整张图判断成无解
怎么知道那些点在路径上?
- 正向建图, 从 \(1\) 出发染色,标记可达点为 \(vis1_i\)
- 反向建图, 从 \(n\) 出发染色,标记可达点为 \(visn_i\)
可以到的点就是两次都被标记的。不用并查集可能是因为是有向图
建图完成后, \(spfa\) 跑最短路
无解情况 :
- \(vis1_n = 0\), 没有路径
- 不等式有负环
答案: 边权是 \(dis_v - dis_u\)
差分约束结论3
给定每\(x_i\)的限制范围,要求\(\sum x_i\) 的最小值,通过差分约束来解决每一个位置的最小值,求 和 的最小值
CF67A Partial Teacher
最小值, 跑最长路
- = 连两条\(i\) 和 \(i - 1\) 的边
- L \(i\) 向 \(i-1\) 为 \(1\) 的边
- R \(i-1\) 向 \(i\) 的为 \(1\) 的边
正常,\(spfa\) 就可以
答案是 \(dis\) 和
另一种做法
先不管 = 号
因为有解, 所以没有环
相当于只一个 \(DAG\)
建边(小的位置往大的连一条边)后拓扑跑
对于一个点的每一条入边带来的权+1,比它大,又尽可能小
等号就把相等的一坨染成一个颜色,当成一个点去做就行了

浙公网安备 33010602011771号