【题解】Patisserie ABC 2 \ Minflip Summation
\(\texttt{ABC200 }\text{Patisserie ABC 2}\)
给定正整数 \(N,K\) 。生成 \(n^3\) 个三元组 \((i,j,k),1\le i,j,k\le N\) ,将它们升序排序,第一、第二、第三关键字分别是: \(i+j+k\) ; \(i\) ; \(j\) 。问第 \(K\) 小的三元组是什么。( \(1\le N\le 1e6,1\le K\le N^3\) )
设 \(\text{cnt}_{sum}\) 代表满足 \(i+j+k=sum\) 的三元组 \((i,j,k),1\le i,j,k\le N\) 的数量,再设 \(\text{CNT}_i=\sum_{j=3}^i \text{cnt}_j\) 。则:
再和 \(f(x)=1+x+x^2+\cdots\) 卷一次,简单地二项式展开和翻转上下指标,就得到了:
由于 \(\text{cnt}\) 恒为正,故 \(\text{CNT}\) 单调增,可以二分确认第 \(K\) 位的 \(i+j+k\) 是多少。
固定了 \(i+j+k\) 的值后,再类似地推导满足 \(j+k=sum\) 的二元组 \((j,k),1\le j,k\le N\) 的数量 \(\text{cnt}'_{sum}\) 的后缀和,通过二分确定 \(i\) ,就可以 \(O(1)\) 确定第 \(K\) 小的三元组。具体地:
后缀和前缀之间互相转化是 \(O(1)\) 的,所以这里类似地推导前缀:
总复杂度 \(O(\log(n))\) 。
组合意义比较强的、多种关键字排序的问题,先考虑一种关键字,通过对一个关键字内的数量求前缀和,二分确定在哪个关键字内,重复做即可。
官方社论里给出的是 \(O(n)\) 的做法,然而如果要加强数据就得上高精了 这个 \(O(\log(n))\) 的做法运算过程中本来就会爆 long long ,如计算组合数的部分。但考察到总共三元组的数量不会爆 long long ,所以求前缀和时必然不会爆 long long ,合理使用 unsigned long long 自动溢出是可行的。
例如,您可以使用如下的代码求解 \(\binom{x}{3}\) :
inline unsigned long long bin3(int x)
{
if(x%6==0) return 1ull*(x/6)*(x-1)*(x-2);
if(x%6==1) return 1ull*(x)*((x-1)/6)*(x-2);
if(x%6==2) return 1ull*(x)*(x-1)*((x-2)/6);
if(x%6==3) return 1ull*(x/3)*((x-1)/2)*(x-2);
if(x%6==4) return 1ull*(x/2)*((x-1)/3)*(x-2);
if(x%6==5) return 1ull*(x)*((x-1)/2)*((x-2)/3);
}
所以放在 \(\text{ABC}\) 里这个数据范围其实比较合适。
\(\square\)
\(\texttt{ABC200 }\text{Minflip Summation}\)
给定由
1,0,?构成的字符串 \(S'\) 和正整数 \(k\) ,从而得到 \(k\) 个 \(S'\) 顺序拼接而成的字符串 \(S\) 。?可以任意地填写1或0,设 \(S'\) 中的?数量为 \(q\) ,这样得到了 \(2^{qk}\) 个新字符串。考虑用最少的步数将每一个新字符串变换成全由1构成的字符串或者由0构成的字符串,变换规则为区间取反。输出这些最少步数的总和。答案模 \(10^9+7\) 。( \(1\le|S'|\le 1e5,1\le k\le 1e9\) )
第一个小 trick 是考虑异或差分,按位异或的逆运算也是按位异或。这样,区间修改就转化为单点修改。目标是使差分数组均变为 0 ,单点修改可以一次只取反一个,也可以一次取反两个,所以只需要考察有几个 01 段和 10 段。设有 \(k\) 个这样的段,则至少需要修改 \(\lfloor\frac{k+1}{2}\rfloor\) 次修改,且可以做到。具体地,两两配对修改后,若还有剩余一个点,再修一次。据此,先考虑不存在 ? 的情况 ,从左往右扫来转移,修改次数增加当且仅当段数从偶数变化到奇数,可以得到:
- 若当前位为
0,那么修改次数增加的充要条件是第一位为1且前一位为1。 - 若当前位为
1,那么修改次数增加的充要条件是第一位为0且前一位为0。
所以,次数的增加与否,仅和第一位和前一位有关。
在加入 ? 后,只需要把 \(\text{mark}_i(\text{第一位},\text{前一位})\) 的推广到 \(\text{cnt}_i(\text{第一位},\text{前一位})\) ,也就是说,某种状态可能不只出现一次,但步数的增加方式是类似的。
设计状态:
简记为 \(\text{A}_i\) 。考虑从第 \(i-1\) 到第 \(i\) 位的转移矩阵 \(M_i\) :
- 若第 \(i\) 位是
0,则转移矩阵 \(\text{Zero}\) :
- 若第 \(i\) 位是
1,则转移矩阵 \(\text{One}\) :
- 若第 \(i\) 位是
?,则转移矩阵 \(\text{Que}=\text{Zero}+\text{One}\)
将 \(k\) 个 \(S'\) 拼接,只需求出 \(\prod_{i=1}^{|S'|}M_i\) 后套个快速幂即可。
总复杂度 \(O(|S'|+\log(k))\) 。
\(\square\)

浙公网安备 33010602011771号