|
|
不会写的做法,不保证正确: 首先发现前缀后缀是否相等可以直接哈希判断,那么这个问题就化为了求 $s_{i+1\sim n-i}$ 的 border。 我并没有发现这个东西可以类 KMP 势能分析均摊 $\mathcal O(1)$ 计算的性质,但是我学过一点点后缀数组,知道 LCP(最长公共前缀)的一个性质: $$\forall 1\le i\lt j\lt k\le n,\text{LCP}(sa_i,sa_k)=\min\{\text{LCP}(sa_i,sa_j),\text{LCP}(sa_j,sa_k)\}$$ 把 $\gt \lceil \frac{n}{2} \rceil$ 的 $sa$ 值标记一下,从前往后递推一遍,得到每个 $sa_i$ 前面第一个被标记过的 $sa$,用 RMQ 求值即可。 时间复杂度 $\mathcal O(n\log n)$,后缀数组常数卡小点估计能过,但一点也不精妙。 定义 $f_i$ 表示 $s_{i+1\sim n-i}$ 的最长不重叠公共前后缀长度。 当我们从大到小枚举 $i$,显然有 $f_i\le f_{i+1}+2$。 从洛谷题解搬的一张图:
那么我们不妨令 $f_i=f_{i+1}+2$,用哈希判合法性,不合法时暴力往前跳。 和 KMP 类似,势能总和为 $n$,那么总的时间复杂度就是 $\mathcal O(n)$。 很有启发的一道题,从中认识到,不能忽视原题中某些「显而易见」的性质,认真分析,它们有可能就是通往正解的钥匙。
题目3794 [POI 2012]Prefixuffix
AAAAAAAAAAAAAAA
10
1 条 评论
2022-11-21 09:02:36
|
|
|
首先不难想到BFS。 以及,箱子能被推动到目标方向当且仅当:①目标方向是空地;②目标方向关于箱子的对面是空地,且人能到达。
如果允许人在空地上任意传送,本题将会简单很多。令 $f_{i,j}$ 表示箱子到达 $(i,j)$ 时的最小次数,每次转移只需判断目标方向的对面是否是空地即可。 但有了沉重货物的限制,会导致人并不一定能到达箱子旁的空地(即使初始时他可以到达)。 不过不难发现,当人推动一次箱子时,他将会“取代”箱子原本的位置。也就是说,判断人是否能到达空地,实际上是判断箱子上次的位置是否能到达那里。而方向只有四个,令 $f_{i,j,0/1/2/3}$ 表示箱子到达 $(i,j)$ ,且上次它在现在的 上/下/左/右 时的最小次数。每次转移时,从上次的位置出发进行搜索,判断是否能到达目标方向对面的空地即可。 时间复杂度大常数$O(n^4)$,无法通过。
上述算法的瓶颈在于,每次转移时都要进行一次搜索,包含了大量的重复计算。我们希望通过一些预处理优化这一过程。 实际上已经很明显了。我们把每个空地抽象成点,向四周的空地连边。箱子放于 $(x,y)$ 时人无法从 $(a,b)$ 到达 $(c,d)$ ,实际上就是说 $(x,y)$ 是原图的一个割点,将 $(a,b)$ 所在连通块与 $(c,d)$ 所在连通块分离。相反,若 $(a,b)$ 与 $(c,d)$ 在同一连通块中,人肯定能相互到达。这样,通过预处理原图的相关$dcc$信息,我们可以做到$O(1)$的转移。 关于 $f$ 的初始化,需要从人的出发点单独搜一次,记录初始时人能到达的箱子旁的空地。 码量稍大,不过每一部分相对简单。
题目240 [POI 1999] 仓库管理员(Store-Keeper)
12
评论
2022-11-20 21:14:10
|
|
|
题目224 [POI 1997] 基因串
8
评论
2022-11-19 00:22:29
|
|
|
Pro894 追查坏牛奶 题解COGS的这一题是超级满配版本 比洛谷的要强力的多:894. 追查坏牛奶 - COGS 额外要求是:求出最小割流量,同时求出割边最小,同时字典序最小的方案 输出割掉的边 最小割流量好求,最小割边的数量也好求,但同时确定哪条边不太好弄,因为存在方法互斥 首先:最小割流量就是跑最大流的结果 求最小割边的数量,需要在刚刚跑完最大流的网络上 把所有的满流边流量重新标记为1,不满流的重新标记为INF 在新的网络上跑一次最大流 这个时候得到的流量就是最小割边的数量 正确性: 满流边一定是某条流量通路的瓶颈路(虽然不一定是唯一瓶颈路) 把满流的边标记成1去跑增广路 得到的结果就是没有公共边的流量通路的条数(因为公共边只允许通过1点流量被计算一次) 那么就给这这些流量通路每个断开一条边即可(如果存在公共边先断开公共边) 如何求最小字典序的方案: 在最小割的情况下 首先要记住,我们一定是优先断开边权最大的必须满流边(删去这条边后,重新对整个网络跑最大流,最大流量会减小这个边的边权那么多(也就是这条边的传递作用无可替代)) 那么找最小字典序方案也出来了:在正常的图上,先跑一次最大流 然后枚举所有边(首先把边按照边权(大到小)-字典序(小到大)两个关键字排序) 先复原整个网络到未增广形态 然后尝试删去这条边,看最大流结果减少的是否是这条边流量那么多 如果是,说明这是关键边,记录这条边会被删除(贪心保证了删除的边数目最少,因为这条边满流,不删它就要删和它在同一支流的多条边) 把这条边永久性删除,并将最大流的结果减小(该边的流量)那么多 这就导致你需要先用正常的边权跑DINIC,再用1和INF的边权跑DINIC,再用正常的边权去找应当被删除的边
题目894 追查坏牛奶
AAAAAAAAAAAA
9
评论
2022-11-15 20:49:14
|
|
|
#include<bits/stdc++.h>
using namespace std;
int t;
int a,b,c;
int main() {
freopen("csp2022pj_pow.in","r",stdin);
freopen("csp2022pj_pow.out","w",stdout);
cin>>a>>b;
c=(pow(a,b));
if(c<0) {
cout<<-1;
} else {
cout<<c;
}
cout<<endl;
return 0;
题目3777 [CSP 2022J]乘方
AAAAAAAAAA
3
1 条 评论
2022-11-12 20:09:18
|
|
|
补充:这个解法是我自己的,相当麻烦,有比我简洁的 DP 做法,还有 dottle 老师的神奇最短路做法,推荐去洛谷题解看看。 首先,看到 $k\le 3$ 的范围,显然是要分类讨论。 k=1显然,最小花费即为 $u\to v$ 在树上路径的点权和。倍增预处理,每次查询 LCA 然后树上前缀和即可。 时间复杂度 $\mathcal O((n+m)\log n)$。 k=2先考虑暴力的做法。将 $u\to v$ 在树上的路径拆下来,将点权写作序列 $b_{1\sim p}$ 研究。 我们用动态规划解决这个问题。设 $f(i)$ 表示 $1\sim i$ 的最小花费。 初始状态:$f(1)=b_1$。 状态转移方程:$f(i)=\min\{f(i-1)+b_i,f(i-2)+b_i\}$。 如果对矩阵很熟悉,不难发现这个就是一个矩阵优化的板子。 不过此处 $b_i$ 是变量,无法进行矩阵快速幂,当时考场上想到这里我脑子莫名其妙宕机了,感觉这题正解绝对是矩阵,但这个东西不会处理啊,然后就彻底蒙了,完全想偏了,最后打了暴力。 实际上和快速幂没有任何关系。因为是树上的静态查询问题,自然可以往倍增想。 因为矩阵满足交换律和结合律,完全可以把矩阵先存起来预处理,最后查询的时候再一次倍增求解。 先把上面那个式子写成矩阵: $$\begin{bmatrix}f(i-1) & f(i-2)\end{bmatrix}\times\begin{bmatrix}a_i & 0\\a_i & +\infty\end{bmatrix}=\begin{bmatrix}f(i) & f(i-1)\end{bmatrix}$$ 为了方便,我们定义 $t=\text{LCA}(u,v)$,$k=3$ 时亦然。 把中间的转移矩阵存起来倍增预处理一下,询问的时候,因为正着走和倒着走没有区别,我们把 $u\to t\to v$ 拆成 $u\to t,v\to t$ 两条链,以 $u\to t$ 为例: 初始向量矩阵: $$\begin{bmatrix}a_u & +\infty \end{bmatrix}$$ 然后把 $fa_u\to t$ 上的转移矩阵全乘起来,就得到了 $u\to t$ 这条链上的答案。 类似地处理 $v\to t$,接下来考虑合并答案。 因为 $k=2$,只有两种可能:$u$ 走到 $t$ 再走到 $v$,或者不经过 $t$,直接从 $t$ 在 $u\to v$ 路径上的两个子节点处穿过。 记 $u\to t$ 的矩阵为 $P$,$v\to t$ 的矩阵为 $Q$,因为可以写作一维向量的形式,为了方便,我们直接将 $P$ 中的元素用类似序列下标的形式表示,即 $P(0),P(1)$。下面 $k=3$ 的情况里我们仍采用这种称呼。 针对两种情况,答案分别为 $P(0)+Q(0)-a_t,P(1)+Q(1)$,两者取 $\text{min}$ 即可。 时空复杂度 $\mathcal O(2^3\times (n+m)\log n)$。 k=3其实 $k=3$ 大体思路和 $k=2$ 完全一致,只不过有一个小细节:答案路径上的节点不一定都是 $u\to v$ 这条链上的。 原因很简单,比如链上的点权都是 $10^9$ 级别,而与链相连的节点中有一个点权是 1,那走这个点显然更优。 题解里大部分做法是将距离设入状态中,我当时并没有想到,而是直接把链接出去的点再设计一个方程。 还是先考虑一条链上的暴力,因为与 $u$ 相连的点中,只有点权最小的有效,设这个最小点权为 $c_u$。 在 $k=2$ 的情况上再加一条:设 $g(i)$ 表示走到 $i$ 连接的点上的最小路径花费。 状态转移方程: $$f(i)=\min\{f(i-1)+a_i,f(i-2)+a_i,f(i-3)+a_i,g(i-1)+a_i,g(i-2)+a_i\}\\g(i)=\min\{f(i-1)+c_i,f(i-2)+c_i,g(i-1)+c_i\}$$ 考虑将这个东西写成矩阵,那么样子就长这样: $$\begin{bmatrix}f(i-1) & f(i-2) & f(i-3) & g(i-1) & g(i-2)\end{bmatrix}\times \begin{bmatrix}a_i & 0 & +\infty & b_i & +\infty\\a_i & +\infty & 0 & b_i & +\infty\\a_i & +\infty & +\infty & +\infty & +\infty\\a_i & +\infty & +\infty & b_i & 0\\a_i & +\infty & +\infty & +\infty & +\infty\end{bmatrix}\\=\begin{bmatrix}f(i) & f(i-1) & f(i - 2) & g(i) & g(i-1)\end{bmatrix}$$ 倍增预处理和查询就很类似了,略过。 最后的合并情况很多,这里我直接把所有情况对应的式子列出来,因为用文字真的很难写出来 QAQ,理解一下叭 awa,有兴趣可以自己推一下,如果实在嫌我的方法麻烦还是看别的大佬的题解吧 qwq: $P(0)+Q(0)-a_t$ $P(3)+ Q(3)-c_t$ $P(1)+Q(1)$ $P(1)+Q(2)$ $P(1)+Q(4)$ $P(4)+Q(1)$ $P(2)+Q(1)$ 所有情况取 $\text{min}$ 即可。时间复杂度 $\mathcal O(5^3\times (n+m)\log n)$。
题目3784 [CSP 2022S]数据传输
AAAAAAAAAAAAAAAAAAAAAAAAA
13
评论
2022-11-09 19:44:30
|