10月做题记录
10月做题记录
✩ trick
✯ 会大部分,要\(tj\)提示
✬ 会小部分/完全没想到,看了\(tj\)才会
◈ 脑电波
✡ 有某一算法的神秘通用性质
⊗ 待补
- 10月做题记录
- CF2018F Speedbreaker Counting ✬✩
- ARC157D YY Garden ✬
- ARC157E XXYX Binary Tree
- ARC157F XY Ladder LCS ✬
- P9062 [Ynoi2002] Adaptive Hsearch&Lsearch ✬✩
- P7599 [APIO2021] 雨林跳跃 ✯
- arc184A Appraiser
- arc184B 123 Set
- arc184C Mountain and Valley Folds ✬
- arc184D Erase Balls 2D
- arc110F Esoswap ✯
- P3641 [APIO2016] 最大差分
- P3777 [APIO2017] 考拉的游戏
- P5473 [NOI2019] I 君的探险 ✯
- arc185D Random Walk on Tree ✬
- CF1523E Crypto Lights
- P4448 [AHOI2018初中组] 球球的排列 ✩✯
- P3236 [HNOI2014] 画框 ✩
- P4155 [SCOI2015] 国旗计划
- CF348D Turtles
- agc068A Circular Distance ✯✩
- agc068B 01 Graph Construction ✯◈
- agc068C Ball Redistribution ✬
- P3765 总统选举 ✯
- [AHOI2005] 航线规划
- CF618G Combining Slimes ✬
- P3239 [HNOI2015] 亚瑟王 ✯✩
- CF804D Expected diameter of a tree
- P3750 [六省联考 2017] 分手是祝愿 ✩✯
- CF1267G Game Relics ✩✯
- CF1392H ZS Shuffles Cards ✬✡✩
- CF1411G No Game No Life ✯
- P8868 [NOIP2022] 比赛
- 单调栈+扫描线做法
- CF2023C C+K+S ✩✯
- CF2023D Many Games ✬✩
CF2018F Speedbreaker Counting ✬✩
非常牛题目,就是学\(whk\)学傻了,乘法过后的取模写掉了,调了两个多小时/ll
首先,这道题是CF2019D Speedbreaker的进化版(?),那么CF2019D Speedbreaker的策略应该有用吧?诶,实际上没用,太邪恶了出题人!
如果你CF2019D Speedbreaker就用了这道题要用的那个很牛的性质当我没说(
这道题要用一个很重要的性质,设区间\(I=[\max i-a_i+1,\min i+a_i-1]\),那么对于序列\(\{a_i\}\),要么能作为起始城市的集合就是\(I\),要么就没有可以作为起始城市的城市
还有一个很重要的策略,对于当前走到的区间\([l,r]\),那么下一步要往右走当且仅当右边存在一个点\(i\),使得\(i-l+1=a_i\),否则就往左边走
可以发现,每个\(\{a_i\}\)对应了唯一一种走法
用这个策略证明该性质:
设\(I=[l,r]\),假设从\([t,t]\)开始(\(t\in[l,r]\)),因为有\(l=\max i-a_i+1\),所以可能向右走的第一步一定是一直向左走到达\(l\)之后,假设在\(p\)处向右走,那么现在的区间为\([p,t]\),那么向右走到的点如果还在\([l,r]\)中,可以继续归类为\([p,t]\),那么现在向右走的点\(q>r\),现在有区间\([p,q]\),显然之后的步骤都一样了,且对于中途,如果有一个\(t\)不能合法的走了,那么所有的\(t\)都无法合法的走,那么得证
下面排除\(I\)中都不合法的情况,即\(I\)就是\(\{a_i\}\)的起始城市的集合
来考虑能不能求出\(I=[l,r]\)的\(\{a_i\}\),直接求等于肯定不太好弄,变为求\([l,r]\in I\)的\(\{a_i\}\),枚举出\(l\)和\(r\),考虑\(dp[i][j][0/1]\),表示\([i,j]\)区间中的方案数,其中\(0\)表示下一步不强制向右走,\(1\)表示强制向右走,那么如果从\([i+1,j]\)转移到\([i,j]\),\(a_i\geq\max(i-l+1,r-i+1,j-i+1)\),从\([i,j-1]\)转移到\([i,j]\)同理有\(a_j\geq\max(j-l+1,r-j+1,j-i+1)\),如果向右走停在\(j\),那么\(a_j=j-i+1\)
这样得到\(O(N^4)\)的解法
明显有很大的优化空间,考虑优化成\(O(N^3)\)的
发现其实\(l\)和\(r\)的具体值不重要,只需要知道它们的相对大小以及\(i\)和\(j\)和它们的相对大小即可
那么现在来处理一个\(2n\)的\(dp\)数组,固定\(r=n\),枚举\(l\),然后\(dp\),显然取对应的\(dp[i][j][0/1]\)即可得到答案
感觉这个算个\(trick\),似乎没咋见过,但是好像又见过,如见(
再来考虑\(O(N^2)\)的做法
我们直接以\(r\)为起始城市来算答案,发现有这样的性质:
- \(i\in[l,\lceil\frac{l+r}2\rceil-1]\),\(a_i\geq r-i+1\)
- \(i\in[\lceil\frac{l+r}2\rceil,r]\),\(a_i\geq i-l+1\)
- \(i\in[1,l)\),\(a_i\geq j-i+1\)
- \(j\in(r,n]\),\(a_j\geq j-i+1\)
且可以知道,从\(r\)会一直走到\(l\),此时才可能会向右走,那么整个过程可以分为两个部分,\(r\rightarrow l\)和之后的步骤
那么\(r\rightarrow l\)间的方案是简单的
考虑之后的步骤,发现与\(l\)和\(r\)无关,于是直接用\(dp[i][j][0/1]\)来算,然后倒着从\(dp[1][n][0]=1\)开始倒着\(dp\)即可
那么对于从\(r\)走到\(l\)后会向右走的\(\{a_i\}\),向右走的第一步就确保了\(l\)的取值就是\(l\),而对于\(r\)走到\(l\)后不向右走的,说明确保\(l\)取到\(l\)的只存在\([l,r]\)内,且可知只能是\([\lceil\frac{l+r}2\rceil,r]\)来确保的,那么分别算出对应的\(a_{[l,r]}\)的方案数,乘上\(dp[l][r][0]/dp[l][r][1]\)即可,记\([l,r]\)的方案数为\(g[l][r]\)
但是可以发现我们只确保了\(l\),没确保\(r\),也就意味着,\(g[l][r]\)记录的实际是\([l,\geq r]\),那么只需要在记录答案的时候变成\(ans[r-l+1]+=g[l][r]-g[l][r+1]\)即可
似乎还看到了\(O(N)\)的做法,有时间再去学一下
感觉这道题咋越写越像\(dp\)用一堆\(trick\)来优化的题(
ARC157D YY Garden ✬
学了一个月\(whk\),糖丸了!尽显唐人气质,鉴定为唐人的课听多了导致的
以前做过?
设 Y
的总数为\(cnt\),首先\(cnt\)是奇数一定无解
那么总共会有\(\frac{cnt}2\)个块,考虑枚举行分成\(a\)块,列分成\(b\)块,显然有\(a\times b=\frac{cnt}2\)
那么进一步的,每一块行中,有\(2b\)个 Y
,每一块列中,有\(2a\)个 Y
,发现在此限制下,分出来的每个块内的点的数量都相等,那么先\(check\)一下,再算方案数即可
合法的\((a,b)\)很小,每次\(O(HW)\)的复杂度,可以过
ARC157E XXYX Binary Tree
擦怎么这也做过
网上的做法
显然会有\(\frac C2\)个非叶节点为 Y
,那么枚举一下根是否为 Y
,即可得到叶子有\(B-\frac C2\)或\(B-\frac C2+1\)个 Y
又因为不存在 YY
,那么 Y
在树上就是独立集,则\(dp[i][j][0/1]\)表示\(i\)的子树内,有\(j\)个叶子是 Y
,\(i\)是否是 Y
,最多能有多少个 Y
那么树上背包即可,复杂度\(O(N^2)\)即可
这就是\(3s\)啊!(感慨)
想到的
前面跟上面差不多,枚举根是否是 Y
,然后确定叶子有几个 Y
,非叶子非根有几个 Y
对于叶子,把 Y
尽量填在兄弟上,然后从低层到高层,尽量给低层的填 Y
即可,显然舍弃低层填 Y
给其父亲填 Y
不优
复杂度\(O(N)\),感觉没啥问题
ARC157F XY Ladder LCS ✬
可以发现,任意三对数必有两组匹配,那么\(ans\geq\frac{2n}3\),那么对于匹配对\((i,j)\),有\(j-i\leq\frac n3\),发现\(\frac n3\)是\(16\)、\(17\)的样子,那么显然状压
设\(dp[i][s]\)表示当前上面遍历到了\(i\),下面可供匹配的为\(s\),那么转移即可
复杂度\(O(N2^{\frac n3})\)
P9062 [Ynoi2002] Adaptive Hsearch&Lsearch ✬✩
套用平面最近点对的网格化做法:选取答案\(L\),然后把平面网格化,划分成\(L\times L\)的格子,每个格子里有\(O(1)\)个点,然后对每个点看其所在格子以及八连通的其余八个格子中的点都拿出来求个距离即可
发现边长取\(L\)的常数倍也是可以的
这道题因为答案\(L\)不确定,考虑找一些特殊的\(L\),需要选取出来的所有的\(L\)能覆盖所有可能的答案,然后找出支配点
那么找到一个\(d\),使得\(L=d^i\),点\(x\)也按照其下标从小到大的枚举,然后\(i\)也从小到大的枚举,找到\(x\)的格子八连通格子,然后遍历里面的点并与之组成一个支配点,最后再把\(x\)插入进去,直接这样复杂度肯定爆炸,所以还要查询后删除\(dis\leq d^{i-1}\)的其他的点,显然合法,且这样的话能保证每个格子内的点都是一个较小的级别,那么支配点近似于\(O(N\log N)\)级别的了
看题解区有人说的是每个格子内\(O(d^4)\)个点,我有个神经的证明能证明是\(O(d^2)\)的(
考虑格子中的一个点\(x\),因为不存在和它距离\(\leq d^{i-1}\)的点,画出以\(x\)为中心,半径为\(\frac{d^{i-1}}2\)的圆,圆在格子中最小的面积为\(\frac 1{16}\pi d^{2i-2}\),格子总面积是\(d^{2i}\)的,那么点数最多就是\(O(\frac{16d^2}{\pi})\)的,也就是\(O(d^2)\)的
好像说因为常数很多,用树状数组维护会被卡常,所以要用\(O(1)-O(\sqrt N)\)的分块维护
总复杂度\(O(N\log N+Q\sqrt N)\),还是太卡常,卡不过/ng
P7599 [APIO2021] 雨林跳跃 ✯
因为一道模拟赛的\(t4\)的结构和这个类似就做了,用笛卡尔树想的,但是树上做很麻烦啊,不如直接序列上做,还是不要太定式思维的好
现在把操作看成,删去序列中所有值小于当前值的数,然后每次可以往左或往右跳
考虑最后一步,设\([c,d]\)中的最大值为\(Y\),当前是\(h_i\),此时能跳到\([c,d]\)中当且仅当\(h_i<Y\),且\((i,d)\)中不存在大于\(h_i\)的值,由此可得,设\([b,c-1]\)的最大值是\(X\),那么\(X<Y\)才能有解,且显然一定有解
那么只要此时的\(h_i\in[X,Y)\),那么就可以一步跳到\([c,d]\)中了,显然让初始的\(h_i\)最大最优,设最初是\(st\),则要满足\([st,b]\)的最大值\(<Y\)
现在来考虑中间的过程,若先不考虑能一步走到终点的情况,那么显然\(h_i\)会跳到左右两侧更大的那一个上去,那么设\(p\)表示\(i\)两侧更大的一侧,来分讨:
- \(h_p\leq X\) 直接跳
- \(h_p\in(X,Y)\) 如果\(p\in[c,d]\),那么一步就可以到终点,否则是两步
- \(h_p=Y\) 一步
- \(h_p>Y\) 从现在起只能向右跳
然后倍增优化过程即可,复杂度\(O((N+Q)\log N)\)
arc184A Appraiser
尝试将序列分成一块一块的,然后询问每个块内元素的关系,若块的大小是\(len\),显然问\(len-1\)次第一个和其他的关系就行
发现\(len=20/21\)比较特殊,若问出来块内和第一个不同的数的数量\(>10\),显然第一个是假币,若相同的数量\(>10\)显然是真币(相同的数量是算上了自身的),此时能确定整个块的情况,而\(len=21\)必满足其一,但\(len=20\)就会出现比较棘手的情况,也就是恰好\(10\)个相同\(10\)个不同
但是发现\(len>20\)都会超过限制,只有当\(len=20\)时,询问次数刚好是\(950\),考虑怎么应付上述的情况
注意到如果当前块是上述情况,那么只需要再用其它块的任意一个数和当前块的第一个数问一次就知道答案了
当这个块是最后一个的时候,在前面算的时候记录一下真币和假币的数量,那么到最后一个的时候就能直接判出来了,此时步数是\(19\times49+19=950\),直接用\(1\)和最后一个块的其中\(19\)个问一下,最后一个可以直接推出来
当它不是最后一个的时候,假设是第\(i\)个(\(i<50\)),步数是\(19\times i+1<950\)
复杂度\(O(N)\)
arc184B 123 Set
画出\(x\rightarrow 2x\),\(x\rightarrow 3x\)的图,发现是一些类似树的结构,每个的开头是一个不含因子\(2/3\)的数
进一步,层数是\(\log_2N\)的,且每一层的数量是\(\lfloor\log_3N\rfloor+1\leq 19\)的,显然可以状压
发现图有很多个,不能全部枚举,但是显然有很多长的一样,具体的\(\lfloor Ni\rfloor\)一样的\(i\)为根的图都长的一样,那么套个根号分治
复杂度\(O(N^{\frac12}\log_2^2N2^{\lfloor\log_3N\rfloor+1})\)
arc184C Mountain and Valley Folds ✬
不会这种题啊,有种好像啥性质的知道但是就是做不出来、看了题解又觉得不难的感觉,怪怪的
发现放置的特点:上一步把当前区间划分成两个区间后,在左边用山谷划分成新的两个区间,右边用山峰划分成新的两个区间
用 v
表示山谷,^
表示山峰
有这样一个性质:把奇数位的折痕都提出来,发现形如 v^v^v^v^...
,证明考虑数学归纳法,只有一个的时候显然是 v
,若当前有\(2^c-1\)个,那么第\(2^c\)会将前\(2^c-1\)反转对称过去,那么显然可以得证
进一步可以发现,对于\(lowbit\)相同的折痕序列,都形如 v^v^v^...
,同样数学归纳法可得证
那么当\(k\)为奇数时,可以确定所有为偶数的\(a_i\)的答案,对于为奇数的\(a_i\)考虑去掉最低位递归求解,\(k\)为偶数时同理
那么可以递归\(solve(i,a)\),\(i\)是二进制位,返回一个二元组\((x,y)\),表示\(k\)的\(2^i\)取\(1/0\)时的答案
对\(a\)分成奇数序列\(b\)和偶数序列\(c\),分别再递归\(solve(i+1,b)\)和\(solve(i+1,c)\),此时前者的\(k\)在\(2^i\)位强制取了\(1\),后者的取了\(0\)
发现对于\(solve(i+1,b)\),\(k\)和\(b\)中的奇数相加的时候是会对\(i+1\)位进位的,所以实际上,对于\(x_b\),表达的是\(k\)的\(2^{i+1}\)是\(0\),对于\(y_b\),表达的是\(k\)的\(2^{i+1}\)是\(1\)
前者可以算出\(x_a\),后者可以算出\(y_a\)
复杂度\(O(N\log A)\)
arc184D Erase Balls 2D
我说我咋做不出来题解也看不懂,原来是看错题了哈哈哈,选择的球不用删啊/ll
记录剩下的球的集合显然不好弄,考虑把剩下球的集合转换成一一对应的选择球的集合
首先,显然选择球会在剩下球中且选择的球间两两不存在偏序关系,那么考虑尽量选球,显然对于集合中,存在偏序关系的球不能选,不存在的能选,那么也就转换成了:除选择的球的外,再任选一个球都会导致删除别的球
\(dp\)即可
复杂度\(O(N^3)\)
arc110F Esoswap ✯
发现对一个点连续操作\(n-1\)次后,这个位置一定变成\(0\)
那么此时自然的会想,能不能从\(0\rightarrow n-1\)逐位确定每一位的值,但是发现我们固定\(0\)后,在固定后面的数的过程中难免会动了\(0\)的位置
那么考虑反着来,先把\(0\)放到\(n-1\)位,然后发现,如果我们继续对\(n-2\)位进行\(n-1\)次操作,那么\(n-2\)位为\(0\),\(n-1\)位为\(1\),由此类推,从\(n-1\)往\(0\)挨个进行\(n-1\)次操作即可,每轮过后序列最后就会变成\(0\sim i\)的样子,证明显然
复杂度\(O(N^2)\)
P3641 [APIO2016] 最大差分
子任务\(1\)
这个就是每次问到最大的和最小的过后递归下去问次小和次大的,这样就能确定所有数的取值
子任务\(2\)
肯定还是要确定最小最大\([l,r]\),然后根据鸽巢原理,\(dis\geq\lfloor\frac{r-l}{n-1}\rfloor\),然后按照\(\lfloor\frac{r-l}{n-1}\rfloor\)分块,每个块内不会有更优的答案
此时最坏\(M=3n-2\)
P3777 [APIO2017] 考拉的游戏
子任务\(1\)
随便给一个点塞个\(1\),然后反悔的为\(0\)的那位是\(1\)
子任务\(2\)
显然一开始放满\(1\)那么返回的有值的位就是\([51,100]\)
由此启发我们缩小范围,且可以知道,同类型的必须放相同的值
在\([51,100]\)数放\(2\),得到\([76,100]\),在\([76,100]\)放\(4\)得到\([92,100]\),在\([92,100]\)放\(11\)得到\([100,100]\)
可以直接去问交互库得证或列出二次函数找单调性即可
子任务\(3\)
由\(2\)启发,我们在\(0\)和\(1\)位置都放\(x\),其他位不放,显然随着\(x\)的增大,\(0\)和\(1\)位的返回值会从两个\(1\),变成一个\(0\)和一个\(1\),再变成两个\(0\),而一\(0\)一\(1\)时就可以确定答案了
同样列出二次函数可知道\(x\geq 15\)一定返回两个\(0\),所以\(x\in[0,14]\)
然后精细点的二分可做到只三次询问
子任务\(4\)
发现询问限制大概是\(O(N\log N)\)的,又因为\(W=200\),那么就可以一次询问来比较两个点的大小,具体的,这两个点都放\(100\)即可
\(stable_sort\)就行,\(sort\)比较鬼畜,不能用
子任务\(5\)
同样考虑缩减范围,如果我们每次都能将\([l,r]\)一步划分成两个不为空的区间,那么操作次数就是\(99\)复合条件的
考虑怎么划分,因为同类型的必须放相同的值,所以考虑给\([l,r]\)都放\(w\),其他放\(0\),那么如果此时返回的值中有\(0\)有\(1\),其中\(0\)有\(k\)个,那么就可以划分成\([l,l+k-1]\)和\([l+k,r]\)
现在只需要找到合法的\(w\)即可,那么用可以枚举选了多少个\([l,r]\)内的数来\(check\)每个\(w\)是否合法
因为\(w=1\)时显然存在\(1\)(因为\(l<r\)),\(w=\lfloor\frac n{r-l+1}\rfloor\)时显然存在\(0\),中间一定是过渡的状态,所以一定存在\(w\)使得有\(0\)有\(1\)
P5473 [NOI2019] I 君的探险 ✯
\(1\sim5\)
直接\(modify\)一个点后询问所有的点即可
\(6\sim9\)
此时相当于是两两配对
考虑二进制,修改当前这一位所有位上为\(1\)的点的状态,然后查询所有点的状态可知与其相连的点的这一位的\(0/1\)
\(10\sim11\)
一棵树,且父节点编号小于当前节点
整体二分出父亲即可
\(12\sim14\)
一条链
同样考虑二进制,分别改了一起修改这一位为\(1\)和\(0\)的点的状态,可以得到与\(x\)相邻的点在这一位的异或值
然后对于\(0\)暴力找到与它相邻的两个点,然后向两侧拓展即可
\(15\sim17\)
无其余限制的树
还是用\(12\sim14\)的办法找出二进制求出\(x\)周围的点的异或和\(v[x]\)
然后往队列\(q\)里塞\(0\sim n-1\),每次取出队首\(x\)并丢掉
如果\(x\)和\(v[x]\)有边,让\(v[v[x]]xor\ x\),然后把\(v[x]\)放到队列中,再让\(v[x]=0\)
如果没有边不操作
\(18\sim25\)
正解是神秘随机化
还是考虑\(10\sim11\)的整体二分,不过此时二分出的是与前一半连边为奇数的点
然后为奇数的往左边递归,整体为奇数且在前一半为偶数的往右边递归
最后能求出一些边,\(check\)一下点,让已经连完了边的弹出我们维护的序列
直接这样做不行,要 random_shuffle
后再弄
有结论:rand的一个排列里面有\(O(\frac n3)\)个点向前连边是奇数个
不会证,很神秘
arc185D Random Walk on Tree ✬
神秘概率期望题/yun
注意到图会成\(n\)条长为\(m\)的链接在一个根上的形式
先考虑\(m=1\)的情况,此时就是菊花图
注意有个重要的期望公式:
设\(E\)表示期望尝试次数,\(p\)表示期望成功概率,\(c\)表示成功时的要花费的代价,那么有\(E=c+(1-p)E\),得到\(E=\frac cp\)
那么设\(f_i\)表示有\(i\)个叶子已经遍历过了的期望从根向叶子节点走的步数,则有\(f_i=f_{i-1}+\frac n{n-i+1}\)
则答案就是\(2\sum_{i=1}^n\frac ni-1\),因为最后一次到底后不用回到根
考虑\(m>1\)的情况
显然调换走的边的顺序不影响答案,因为走的边的总数不变,所以考虑把根走到一棵子树中的所有操作都放在一起
那么现在就同样分成了\(n\)个部分,每个部分里存储了从根向该子树走的所有边
考虑从根直走到链底的期望步数,此时根和链底都只能往一个方向走
设\(g_i\)表示深度为\(i\)的节点走到链底的期望步数,那么有:
手算出前几项可以发现,\(g_0=m^2\)
那么答案就是\(m^2\times(2\sum_{i=1}^n\frac ni-1)\)
CF1523E Crypto Lights
设\(f(i)\)表示放\(1\sim i\)的台灯都合法,第\(i+1\)个不合法
答案即为\(\sum f(i)\times(i+1)\),因为\(k\geq 2\),所以不用考虑放满的情况
然后有两种方法,一种是直接算\(f(i)\),另一种是做\(f(i)\)的后缀和数组\(g(i)\)表示保证\(1\sim i-1\)合法,答案为\(\sum g(i)\)
那么有\(f(i)=\frac{(n-i-1)!}{n!}\times(i+1)\times(A_{n-(i-1)(k-1)}^{i}(n-i)-A_{n-i(k-1)}^{i+1})\)
\(g(i)=A_{n-\max(0,i-2)(k-2)}^{i-1}\times\frac{(n-i+1)!}{n!}\)
复杂度\(O(TN)\)
P4448 [AHOI2018初中组] 球球的排列 ✩✯
好久没做组合了,这么经典的\(trick\)都忘了/xia
首先发现乘积为平方的当且仅当它们每一个质因子的质数的奇偶性都相同,那么就可以划分出一些等价类,每个等价类中的数两两间相乘都是平方数,不同等价类的两个数相乘一定不是平方数
设有\(k\)个等价类,设\(sz_i\)表示第\(i\)个等价类的大小,\(b_i\)表示这个等价类中至少有\(i\)对相邻的
发现题目要求的是等价类内的数也要有序,但是如果有序我们就难以在算方案时做到不重,那么考虑先变成无序的,把\(\prod(sz_i!)\)提到外面,现在只需要处理无序的问题了
答案就是:
用背包优化一下即可
复杂度\(O(N^2)\)
P3236 [HNOI2014] 画框 ✩
最小乘积生成树,点是\((\sum A_{i,p_i},\sum B_{i,p_i})\)
每次让\(i\rightarrow j\)的边权是\((y_a-y_b)A_{i,j}+(x_b-x_a)B_{i,j}\),然后跑费用流最小费用最大流即可,好像卡费用流啊,要用\(KM\)
P4155 [SCOI2015] 国旗计划
有个有趣的线性做法
倍增的\(O(N\log N)\)做法是显然的,考虑连出边,建出树,然后对应每个点有个决策点,决策点每次不动或者向下移动一位,这样复杂度就是\(O(N)\)的了
CF348D Turtles
容斥
肯定一条路径是\((1,2)\rightarrow(n-1,m)\),另一条是\((2,1)\rightarrow(n,m-1)\)
发现路径存在交集的时候,把第一个交集到\((1,2)/(2,1)\)的路段换一个走法,即让第一条是\((1,2)\rightarrow(n,m-1)\),第二条是\((2,1)\rightarrow(n-1,m)\),这样必然有交且能和原来的走法中存在交的走法一一对应
\(lgv\)板子
起点定为\((1,2)\)和(2,1)\(,终点定为\)(n-1,m)\(和\)(n,m-1)\(,就是\)lgv$板子了
agc068A Circular Distance ✯✩
恰好肯定不好求,考虑求答案距离\(\leq\)或\(\geq\) \(i\)的方案数
发现\(\geq i\)不好去重,来考虑\(\leq i\)
设\(f(i)\)表示选出的点的答案距离\(\leq i\)的方案数,那么我们钦定\(0\)点会被选,算出这个的方案数再乘上\(\frac ln\)即可
此时因为\(0\)点必选,所以其他的点一定在\([1,i]\)或\([l-i,l-1]\)中
同属于一个区间的点间显然没有限制,考虑区间之间的点的限制,因为这个限制是相对的,所以我们来考虑\(x\in[l-i,l-1]\)中的点对\([1,i]\)中的点的限制
发现选了\(x\)点后,\([x+i+1-l,x-i-1]\)就不能选
这里有个很巧妙的办法,把\([l-i,l-1]\)整体平移到\([1,i]\)去,那么现在的限制就是原本的\([1,i]\)中的\([x,x-2i-2+l]\)不能选,设\(len=l-2i-2\),即\([x,x+len]\)中的点不能选
太巧妙/se
现在就可以变成这样一个问题:给你\(i\)个点,每个点可以染成\(0/1\)或不染色,\(0\)对应选了原本的\([1,i]\),\(1\)对应选了原本的\([l-i,l-1]\),不染色就是不选,然后要求每个\(1\)后面的第一个\(0\)到这个\(1\)的距离\(>len\),要求染色的点有\(n-1\)个
这样问题就边的简单了,枚举\(j\)表示这\(n-1\)个染色点中有多少相邻对的 10
的形式,留出它们的间隙,那么选点的方案数就是\(C_{i-j\times len}^n-1\),然后来考虑具体怎么给这个\(n-1\)个点染色,发现直接这样看是可能会有\(2j/2j+1/2j+2\)段同色连续段的,但是如果我们在这些点前放一个\(0\)色点,这样这\(n\)个点就有\(2j+1/2j+2\)个同色连续段了,继续在这些点后面放一个\(1\)色点,这\(n+1\)个点就有\(2j+2\)个同色连续段了,插板法即可,方案数\(C_n^{2j+1}\)
算简化运算的\(trick\)?
因为有要求\(i-j\times len>=n-1\)且\(2j+1>=n\),所以枚举\(i\)再枚举\(j\)的复杂度就是调和级数\(O(N\ln N)\)的
agc068B 01 Graph Construction ✯◈
蓝色的,但构造题,不会呜呜/ll
考虑一开始\(S\)放\(n\)个\(0\),\(T\)放\(n\)个\(1\),这样有个好处,\(1\sim n\)之间不会直接连边,我们考虑让它们在后面某个点处相连
取出同色的所有相邻的点,只要能让这些点间有边,就能满足题意了
发现在\(S\)和\(T\)的末尾同时放一个\(0/1\),就相当于把\(S\)开头的第一个\(0\)/\(T\)开头的第一个\(1\)转移到了末尾去
那么我们只需要讲当前需要连边的点对\((u,v)\)分别转移到\(S\)的开头和\(T\)的开头(即将它们之前的放到末尾去),然后在\(S\)和\(T\)的末尾再操作两次,先分别加上\((1,0)\),再分别加上\((0,1)\),这样就让它们相连的同时,把它们也转移到了末尾
复杂度\(O(N^2)\)
agc068C Ball Redistribution ✬
正着肯定不好做,考虑倒着做
先建图\(i\rightarrow a_i\),那么得到了内向基环树森林,对于一次操作,正着就是把所有连向\(i\)的点都提出来连成一个环,那么倒着就是提一个环拆掉让环上所有点都连向\(i\),且要满足原先就连向\(i\)的点一定在环上
那么显然如果有某一步使得原先连向\(i\)的点不在环上就不合法了
直接做是不好做的,考虑找个充要条件
手摸一下数据后可以发现,对于\(u\)的一个儿子\(v\)(即\(v\)不在环上),如果\(v\)子树中存在点\(x>u\),那么一定可以用以下策略构造合法解:\(i\)从\(n\rightarrow1\)遍历,然后每次把\(i\)所处连通块的环拆了连向\(i\),可以发现,这样每个\(i\),要么没有孩子,要么孩子一定都在环中,且这种策略下,若有\(u\)不存在\(v\)满足\(v\)子树中存在点\(x>u\),那么一定不合法
再来考虑后面这种情况,发现此时操作\(u\)前,其子树\(v\)是一定不可能被操作的,因为没有环,即会保持原样,那么操作\(u\)时,显然\(v\)就是那个不在环上的儿子,那么确实就是一定不合法的
所以直接\(dfs\)判即可
复杂度\(O(N)\)
P3765 总统选举 ✯
数据结构
正常的做法就是用线段树维护摩尔投票和平衡树维护每个值的点,平衡树改成线段树也可以,就是这样空间更大
原本写的是
正常的做法就是线段树+平衡树,线段树+线段树也可以,就是这样空间更大
,小登以为我说的是树套树,又把我\(jue\)了一顿/ll,遂改没树枝小登,真给我踩了。。。
随机化 ✯
然后牛的是随机化做法,取一个\(k\),然后在区间中随机\(k\)个数,对于每个选出的数都去平衡树里判一下是不是绝对众数,若存在绝对众数但选\(k\)个都没选到的概率最大都是\(\frac1{2^k}\)
分块
无所不能的根号分治啊,怎么有人啥都能来分两手啊
设阈值\(B\),若查询区间\(\leq B\),直接暴力查了,若查询区间长度\(>B\),绝对众数至少有\(\frac B2\)个,这样的数字只有\(\frac{2N}B\)个,然后对每个这样的数都去线段树/平衡树上查一下就行
\(B\)取\(\sqrt{2N\log N}\)复杂度\(O(Q\sqrt{N\log N}+\sum k\log n)\)
[AHOI2005] 航线规划
\(OIwiki\)用作的维护边双连通分量的例题啊,提供另一种做法,更简便
\(LCT\)做法
给边单独建点,然后夹在其连接的两点之间即可,然后考虑倒着操作,就是加边,如果不连通就\(link\),连通就把这条链上所有点的权值变成\(0\),初始边点的权值是\(1\),普通点的权值是\(0\)
复杂度\(O(M\log N)\)
CF618G Combining Slimes ✬
考虑最终的序列呈什么样子,肯定会是一些下降段的拼接,而每个下降段的末尾都是\(1\)(最后一个下降段可能不是),每个下降段最开始都是先放了一个\(2\)(第一个下降段可能不是)
因为显然对于一个序列,满足它当前末尾不是\(1\),然后发现当且仅当你塞一个\(1\)再塞一个\(2\),会使得\(1\)及其左侧的部分后面都不会再被操作了
那么现在的大概方向就是想要求出每一段的答案然后拼起来,然后每一段的分隔是用\(1\)来分隔的
又可以发现,设序列最大值是\(m\),概率大概可以表示为\((p^2+1-p)^m\),则\(m>50\)时几乎就是\(0\)了,所以我们的数最大取到\(50\)即可
设\(dp[i][j]\)表示现在序列长度为\(i\),且最左侧是\(j\)的序列的和的期望
对于\(j>1\),\(dp[i][j]=\frac{\sum_{k=1}^{j-1}dp[i-1][k]\times f[i-1][k]}{\sum_{k=1}^{j-1}f[i-1][k]}\)
当时推到这里迷惑为啥是\(f\)不是\(f'\),因为看似这个式子后面的转移保证了后\(i-1\)个的第一个是\(<j\)的
总的期望不是概率\(\times\)权值吗,但实际上发现它只是保证了你当前算出来的权值是合法的,本来就应该是合法的概率\(\times\)合法的权值
这里\(f[i][j]\)表示长度为\(i\)的序列,最左侧是\(j\)的概率
要转移到这个,肯定还需要\(f'[i][j]\)表示长度为\(i\)的序列,最左侧出现过\(j\)的概率,显然\(f'[i][j]=f'[i][j-1]\times f'[i-1][j-1]\),\(j=1/2\)要初始化
然后有\(f[i][j]=f'[i][j]\times(1-f'[i-1][j])\)
关于这些转移:
首先有:只关注最左侧的数,所以后面的数长什么样的不重要
其次,显然我们的这个过程是可
对于\(f'\),要想最左侧拼出一个\(j\),就是先拼出一个\(j-1\)放在最左边,再用剩下的\(i-1\)位拼出一个\(j-1\),然后它们能合并成\(j\)
然后又因为上面所说的下降段的性质,所以如果现在拼出来了一个\(j\),要想最左侧是\(j\),即不会再出现\(j\)和这个\(j\)进行合并了,也即在后面的\(i-1\)位的第一个下降段中,不会出现\(\geq j\)的数,也即后\(i-1\)个的最左侧那个\(<j\)即可,又注意到\(f'\)的定义是
出现过
,那么反向考虑,没出现过\(j\)的概率也就是最左始终\(<j\),那么转移就得出了
而\(dp\)的转移对于\(j=1\)时,有\(dp[i][j]=\frac{\sum_{k\geq2}dp[i-1][k]\times g[i-1][k]}{\sum_{k\geq2}g[i-1][k]}\),其中\(g[i][j]\)表示长度为\(i\)的序列,最左侧是\(j\)且第一个放的是\(2\)的概率
同理,\(g'[i][j]=g'[i][j-1]\times f'[i-1][j-1]\),\(g[i][j]=g'[i][j]\times(1-g'[i-1][j])\)
最终的答案就是\(\sum_j dp[n][j]\times f[n][j]\),因为\(f[i][j]\)当\(i>m\)时,有\(f[i][j]\approx f[m][j]\),所以答案式子变成\(\sum_j dp[n][j]\times f[m][j]\),那么\(dp\)可以快速幂
复杂度\(O(M^3\log N)\)
P3239 [HNOI2015] 亚瑟王 ✯✩
首先,根据期望的线性性,算出每个卡牌被发动的概率,再乘上对应的伤害就可得到总的期望
考虑怎么算出每个卡牌被发动的期望
先来考虑第一张卡牌发动的概率,一下可能会想到枚举它是在第几轮被选择发动的,但是比较麻烦,对于后面的卡牌的计算也没啥可推广性,考虑容斥,即用总概率减去\(r\)轮都选不到第一张卡牌的概率,那么就是\(1-(1-p_1)^r\)
再来想第二张卡牌,如果第一张一直没选,该情况下,选第二张的概率就是\(1-(1-p_2)^r\);如果第一张选了,看似要讨论第一张比第二张先选还是后选,但是发现因为我们是在用 总的概率
减去 一直都没选到的概率
,而这个 一直都没选到的概率
因为一直都没选,所以就根本不用考虑当前这张是比前面某一张先选还是后选,所以此时的概率就是\(1-(1-p_2)^{r-1}\),因为选第一张的那一轮第二张根本不会存在选择是选还是不选的问题
那么就知道了,如果\(r\)轮操作下,\(1\sim i-1\)选了\(j\)张,那么第\(i\)张被选的概率就是\(1-(1-p_i)^{r-j}\)
剩下的部分就显然了,考虑\(dp[i][j]\)表示前\(i\)张选了\(j\)张的概率,转移有:
答案就是:
\(Ans=\sum_{i=1}^n \sum_j dp[i-1][j]\times(1-(1-p_i)^{r-j})\times d_i\)
复杂度\(O(N^2)\)
CF804D Expected diameter of a tree
显然,伪的期望,根号分治即可
复杂度\(O(N\sqrt N)\)
P3750 [六省联考 2017] 分手是祝愿 ✩✯
怎么像没学过概率与期望一样,看啥都是\(trick\)
首先可以发现,最优策略一定是从大到小,如果当前点状态为\(1\)就操作,否则不操作,那么对于给定的数组可以\(O(N\log N)\)的找出最优策略
再来考虑随机选点,发现对于当前序列,最优策略是\(t\)步,随机选点一次后会变成\(t+1/t-1\)步,具体的,如果选中了最优策略中的点就是\(t-1\)步,选中了这之外的点就是\(t+1\)步,因为显然我们的任意一个点的操作都不能被其它点的操作凑出来
那么这时就可以考虑\(dp\)了,状态就是最优策略的点数
这里我当时想到的是\(dp[i]\)表示最优策略点数为\(i\)时的期望,发现这样虽然可以\(O(N)\)转移,但是无法确定初始化
有个\(trick\)就是设\(dp[i]\)表示最优策略点数从\(i\)变成\(i-1\)的期望,转移为\(dp[i]=\frac{n-i}n(1+f[i+1]+f[i])+\frac in\),初始化\(f[n]=1\)
那么答案就是\(n!(k+\sum_{i=k+1}^{s_0}f[i])\),\(s_0\)是初始的最优策略点数,如果\(s_0\leq k\),答案就是\(n!s_0\)了
复杂度\(O(N\log N)\)
CF1267G Game Relics ✩✯
首先能注意到\(c_i\leq x\),可以猜测最开始一定是先随机,然后最后再直接买
考虑在已有\(i\)个的情况下,随出一个新的数的期望\(f_i=\frac in(\frac x2+f_i)+\frac{n-i}nx\),化简得\(f_i=\frac i{2(n-i)}x+x\),显然随着\(i\)的增大,\(f_i\)也在增大
考虑什么时候会从随机转变成直接买,设已经随机了\(i\)个,它们的\(c\)之和为\(j\),那么如果现在变成买,代价就是\(sum-j\),这里有个\(trick\),给它平摊一下,那么每选一个的代价就是\(\frac{sum-j}{n-i}\),那么此时直接比对\(\frac{sum-j}{n-i}\)和\(f_i\)的大小就能知道选那种操作了,且显然\(f_i\)在增大,如果当前前者更优,之后前者都会比\(f_i\)更优
复杂度\(O(N^3+N^2V)\)
CF1392H ZS Shuffles Cards ✬✡✩
首先我们可以得到:\(Ans=E(轮数)\times E(每轮抽牌数量)\),这是显然的
考虑\(E(每轮抽牌数量)\),我们令操作变成每轮抽卡都要把卡抽完才结束,但只有第一张鬼牌及其之前的卡会被计入数量,那么\(E(每轮抽牌数量)=E(每轮被计数的数字牌)+1\),而每个数字牌比所有鬼牌都先抽到的概率是\(\frac 1{m+1}\),所以\(E(每轮抽牌数量)=\frac 1{m+1}+1\)
考虑\(E(轮数)\),它可以表示为\(\sum_iE(还剩i张数字牌时抽到新的数字牌的轮数)+1\),这里我们的\(E(还剩i张数字牌时抽到新的数字牌的轮数)\)是一个左闭右开形式,即包含了不包含刚好抽到新数字牌的那一轮的,这一轮算在\(i-1\)的\(E\)里,因为不这样会算重
下面简化的称之为\(E(i)\),那么在第一张鬼牌前存在新牌的概率是\(\frac i{m+i}\),所以\(E(i)=\frac{m+i}i-1=\frac mi\),这个\(-1\)就是去掉包含抽到新牌的那一轮
那么\(Ans=(\frac 1{m+1}+1)(m\sum_{i=1}^n\frac 1i+1)\)
CF1411G No Game No Life ✯
很典的模型,每个芯片都是一个独立的模型,它们的\(sg\)值的异或和就是答案,可以先\(O(M)\)的求出每个点的\(sg\)值
然后我当时这里想的就是\(trie\)数+组合数乱算,算出后手赢即最终\(sg=0\)的概率,然后发现有些过于麻烦,放弃了
可以考虑设\(f(x)\)表示若初始局面的\(sg\)值是\(x\),先手胜的概率,那么有:
然后高斯消元就行
还有神秘\(FWT\)做法啊,先不打算做,咕咕咕
复杂度\(O(M^{\frac32})\)
P8868 [NOIP2022] 比赛
解法直接co聊天内容了啊(
分治做法
它分治的做法的话
就是考虑离线,然后把询问挂到区间上
具体就是,跨过了这个区间的中点就挂到区间上
然后如果完全包含了这个区间,这个区间下面的区间就不用挂了
然后询问的话,考虑枚举右端点
设右端点是i
然后大概有两种情况
一种是a和b的最大值都在同一侧
另一种是异侧
然后就先考虑a的最大值在右边的情况
此时可以发现
首先左端点会有一个限制
设它要>=j
然后j-1就满足是边界或者a[j-1]>mid+1~i的最大的a
然后发现会存在一个k
左端点<k的,b的最大值在左侧
=k的在右侧
然后考虑每个i的贡献
对于[j,k)的左端点p,就是bmax[p,mid]*amax[mid+1,i]
[k,mid]的是bmax[mid+1,i]*amax[mid+1,i]
然后就可以线段树维护每个点作为左端点时的贡献
查询答案的话,如果一个区间[l,r]的r=i
那么就能得到[l,mid]中的点贡献
双log
单调栈+扫描线做法
就扫描右端点,然后维护一个a和b的下降的单调栈
设右端点还是i,左端点是j
然后此时j的贡献就是在单调栈上下标>=j的最小的两个a和b的值的乘积
然后考虑加入a[i]和b[i]的影响
还是可以线段树维护
先考虑如果加入进去,栈没有弹出的话
就两个栈都不弹出
此时左端点j的贡献不变,这个就可以打tag
增加一个新的左端点j=i的值
就类似区间修改,++tag,然后维护区间内所有j的此时的贡献,就是a*b的值
然后如果栈有弹出
其实就是区间修改一个后缀
那么线段树维护就行了
单log的
CF2023C C+K+S ✩✯
蓝题都不会了喵/ll,染色\(trick\)根本没想到喵
因为是强连通图且环长保证为\(k\),所以可以给每个点染\(0\sim k-1\)的色,然后若存在边\(u\rightarrow v\),就要求\(v\)的颜色值是\(u\)的颜色值\(+1\)然后\(\mod k\)
得出\(A\)图和\(B\)图每个点的染色,然后,就是要它们的颜色数组成循环位移的关系
然后\(hash\)不知道行不行啊,感觉可能会冲突?毕竟总的数量太多了,总之\(kmp\)可以
复杂度\(O(N)\)
CF2023D Many Games ✬✩
啥\(trick\)啊,疯狂给\(dp\)剪枝了属于是
一开始试图找一些结论,未果,考虑背包,能作背包的就\(\prod\frac{p_i}{100}\)和\(\sum w_i\),显然只能是\(\sum w_i\)
发现题目给了一个神秘的性质,\(p_i\times w_i\leq2e5\),猜测能用来限制我们的\(\sum w_i\)的大小
考虑最优解集合\(S\),那么此时去掉其中任意一个数\(j\)都不优,即有:
注意到\(\frac{100}{100-p_j}>p_j\)当且仅当\(p_j=1\)时成立,因为\(100p_j-p_j^2\)是二次函数,画出图像易证,那么只要\(p_j>1\),都有\(\sum_{i\in S}w_i\leq w_j\times\frac{100}{100-p_j}\leq w_j\times p_j\leq2e5\),当\(p_j=1\)时,大概取到\(202020\)
那么我们\(dp\)的状态就是\(O(2.1e5)\)级别的了
考虑转移的复杂度,按\(p_i\)对物品进行分类,有显然正确的想法,若要取\(k\)个,则取\(p_i\)中\(w_i\)前\(k\)大的
考虑\(p_i\)中最多取\(k\)个,如果就取\(k+1\)个\(p_i\)不优于就取\(k\)个\(p_i\),那么显然最优答案就不可能会有\(k+1\)个\(p_i\),这个易证
设前\(k\)大的\(w_i\)之和为\(S\),第\(k\)大的\(w_i\)为\(v\),\(p=\frac{p_i}{100}\)
那么有式子
那么转移就是\(O(100\log_2100)\)的级别
总复杂度大概\(O(2.1e5\times100\log_2100)\),绰绰有余(