Luogu P11696 [JRKSJ ExR] 七影蝶

对 \(\operatorname{popcount}(x)\) 有一个经典的处理是拆位,\(w\) 位为 \(1\) 当且仅当 \(x\bmod 2^{w + 1}\in [2^w, 2^{w + 1})\),所以 \(a_{i} + x\) 在 \(w\) 位为 \(1\) 当且仅当 \(x\bmod 2^{w + 1}\in [2^w - a_{i}, 2^{w + 1} - a_{i})\)(循环意义下)。

在 \(\bmod 2^w\) 情况下考虑,那么只需要去掉 \(w\) 这一位就可以变为 \(\bmod 2^{w - 1}\) 的情况,所以尝试从低位往高位递推信息。

考察需要的信息,发现单考虑 \(\bmod 2^{w + 1}\) 的信息,只有 \(2^{w} - a_{i}, 2^{w + 1} - a_{i}\) 以及询问的 \(l_{i}\bmod 2^{w + 1}, (r_{i} + 1)\bmod 2^{w + 1}\)(把询问拆成开区间 \([l, r)\))这些端点会带来一些不同的信息。
换句话说,如果两个 \(x, x'\) 取到 \(\operatorname{popcount} = 1\) 的 \(a_{i}\) 以及包含其的询问集合均一样,就认为这两个点等价,那么保留上述 \(2n + 2q\) 个端点(再加入 \(0, 2^{w + 1}\) 两个哨兵端点),相邻两端点代表的区间 \([l, r)\) 内的 \(x\) 一定都是等价的。

于是现在尝试只维护每个段的信息,不过有一个问题是 \(\bmod 2^{w + 1}\) 的端点应该要满足 \(\bmod 2^w\) 时也为端点,不然相当于劈开了 \(\bmod 2^w\) 的一个段,被劈开的段就不能一同考虑。
发现 \(((2^{w} - a_{i})\bmod 2^{w + 1}) \bmod 2^w = (2^{w} - a_{i})\bmod 2^w, (2^{w + 1}\bmod 2^{w + 1})\bmod 2^w = -a_{i} \bmod 2^w = (2^w - a_{i})\bmod 2^w\),\(l_{i}, r_{i}\) 也是同理的。也就是说 \(\bmod 2^{w + 1}\) 的端点 \(\bmod 2^w\) 后也是 \(\bmod 2^w\) 后本身带有的端点。
那么把 \(\bmod 2^w\) 的段复制一遍拼在后面(就相当于加了高位变为了 \(\bmod 2^{w + 1}\) 的情况),\(\bmod 2^{w + 1}\) 的每个段一定是若干个连续的段接起来的,而合并只需要取 \(\max\),且因为带顺序可以直接维护指针顺序扫描的时候合并。

\(\operatorname{popcount}\) 的贡献也只需要做个前缀和。

最后算答案的时候 \([l_{i}, r_{i})\) 应该对应到 \(\bmod 2^{\lfloor \log V\rfloor + 2}\) 的一部分连续的段,只需要用线段树再查个区间 \(\max\) 即可。

时间复杂度为 \(\mathrm{O}((n + q)\log (n + q)\log V)\),空间线性。

复杂度 \(\log (n + q)\) 的原因是对每一个 \(\bmod 2^w\) 需要对端点排序,并且 \(\operatorname{popcount}\) 的贡献需要二分找端点。
因为这是按照 \(w\) 变大处理的,改为基排,二分找端点变为维护指针做到线性,时间复杂度 \(\mathrm {O}((n + q)(\log (n + q) + \log V))\),空间还是线性。

posted @ 2026-10-26 16:35  rizynvu  阅读(10)  评论(0)    收藏  举报