CF2039

传送门

A:取 \(a_i=2i-1\) 即可。

B:注意到如果有连续三个相邻不同字符,这个长度为 \(3\) 的子串满足;如果有相邻两个字符相同,这个长度为 \(2\) 的子串满足。否则字符串形如 \(ababab\dots\),没有子串满足。

C1:数学太拉了

题意:给定正整数 \(x,m\),计数 \(y\in [1,m]\)\(x\neq y\)\(x,y\) 中有至少一个是 \(x\oplus y\) 的倍数。(\(x\le 10^6,m\le 10^{18}\)

分析:

因为 \(x,y>0\),所以 \(x\oplus y<x,y\),所以 \(x\oplus y\) 必定是真因数。

而一个数的真因数 \(\le\) 它的 \(\dfrac{1}{2}\),所以要使得 \(a\)\(b\) 的真因数,\(a\le [\dfrac{b}{2}]\),所以 \(a\) 至少二进制比 \(b\) 少一位。

而当 \(y\ge 2\cdot x\) 时,\(x\oplus y\)\(y\) 的二进制位数相等,所以 \(x\oplus y\) 不是 \(y\) 的因子;而且此时它比 \(x\) 大,也不可能是 \(x\) 的因子。

所以:合法的 \(y\) 总是 \(< 2\cdot x\)

因此枚举 \(i=1\sim 2x-1\) 检验即可。

C2:数学太拉了

题意:给定正整数 \(x,m\),计数 \(y\in [1,m]\)\(x\neq y\)\(x,y\) 中有至少一个是 \(x\oplus y\)因数。(\(x\le 10^6,m\le 10^{18}\)

分类讨论。依次考虑 \(x\oplus y\)\(x,y\)\(x,y\) 的因数。

  1. \(x\)\(x\oplus y\) 的因数。\(p=x\oplus y\),问题转化为求有多少个 \(p\) 使得 \(x\)\(p\) 的因数且 \(1\le p\oplus x\le m\)

    异或性质:\(p\oplus x\le p+x\) 所以当 \(p\le m-x\) 时,\(1\le p\oplus x\le m\) 总是满足,只需要保证 \(x\)\(p\) 的因数即可。这等价于问 \(x\)\(1\sim m-x\) 里有多少个它的倍数,答案是 \([\dfrac{m-x}{x}]\)

    那对于 \(p>m-x\) 的呢?再异或性质:\(p\oplus x\ge p-x\),所以当 \(p>m+x\) 时,\(p\oplus x\le m\) 总是不满足

    因此这种情况剩下可能合法的 \(p\) 只存在于 \((m-x,m+x]\) 里,暴力枚举检验。

  2. \(y\)\(x\oplus y\) 的因数。因为有了上面的观察:\(x\oplus y\le x+y\)这限制了异或的范围),所以当 \(x<y\) 时,\(x+y\le x+y<2y\),这时候 \(y\) 要是 \(x\oplus y\) 的因数只能 \(x=0\),无解。

    所以剩下的情况只有 \(x>y\) 的情况,因此枚举 \(y=1\sim x\) 检验即可。

  3. \(x,y\) 都是 \(x\oplus y\) 的因数。

    转化:\(\mathrm{lcm}(x,y)\)\(x\oplus y\) 因数。

    \(x\oplus y\le x+y\),而 \(\mathrm{lcm}(x,y)\)\(x\neq y\)\(\ge 2\max(x,y)\),所以当 \(x\neq y\) 时不可能合法。

    检验 \(y=x\) 即可。

D:

题意:给定数集 \(S\),要求构造一个(或判定无解)字典序最大的 \(n\) 长度序列 \(\{a_i\}\),使得 \(a_i\in S\)\(a_{gcd(i,j)}\neq gcd(a_i,a_j)\)。(\(n,|S|\le 10^5,a_i\le n\)

\(a_{gcd(i,j)}\neq gcd(a_i,a_j)\) 的条件很迷惑。取 \(i\)\(j\) 的因数,就得出结论:对于任意 \(i\mid j\),不能有 \(a_i\mid a_j\)

那么这个条件是否是充分的?假设 \(a_g=gcd(a_i,a_j)\),其中 \(g=gcd(i,j)\),则 \(a_g\mid a_i\),与 \(a_i\not\mid a_j\) 矛盾。所以是充分条件。

法一:贪心法。枚举 \(i=1\sim n\),每次都选与前面不干扰的最大数。(赛时想到了,然而没想到上面的结论所以是假复杂度)

实现方法:枚举位置 \(i\) 的因数 \(j\)(均摊 \(O(n\log n)\))。然后给数 \(a_j\) 打上标记,再从大到小枚举找第一个打标记的即可。

法二:考虑 \(i\rightarrow ki\) 建立一个 DAG,那么位置 \(i\) 能填的数的大小仅与在 DAG 上以 \(i\) 开头的最长链长度有关,可以用 DP 求出;因为边的总数是 \(O(n\log n)\) 的。

如果你仔细分析,发现这个值等于 \(i\) 的各质因数次数之和 \(+1\)

E:巧妙 DP 题。

题意:给定初始序列 \(a=\{0,1\}\)。每次可以将 "当前序列的逆序对数" 插入序列的任意位置,问有多少种可能的 \(n\) 长度序列。\(n\le 10^6\)

来自 Byf 的观察:记 \(f_i=i\cdot f_{i-1}-1\),答案为 \(\sum_{i=1}^n f_i\)

解法:

注意到当逆序对数大于序列内任何一个数之后,如果不将它插在末尾,新的逆序对数仍然大于序列内任何一个数。

\(dp[i]\) 表示当前序列为 \(i\) 长度且逆序对数大于序列内任何一个数,能构造出多少种 \(n\) 长度的序列。

如果不插入到末尾,\(dp[i]\leftarrow dp[i+1]\);否则枚举插入 \(j\) 个到末尾,然后随便插入一个在前 \(i\) 个里面(\(i\) 种方式),\(dp[i]\leftarrow i\cdot dp[i+j+1]\)。注意可以直接在末尾插到 \(n\) 长度。

在求出 \(dp[i]\) 后,我们的问题变成第一次逆序对大于序列内任何数的位置在哪里。初始序列是 \(\{0,1\}\),也就是只要出现逆序对 \(2\) 就可以了。

初始逆序对数为 \(0\)。逆序对数将一直为 \(0\) 直到第一次插入 \(0\) 至末尾,此时逆序对数为 \(1\)
然后为了保持逆序对不达到 \(2\)\(1\) 只能一直插入在末尾的那一块。

所以,逆序对 \(\le 1\) 的序列必然形如 \(0,0,0,\dots,0,0,1,0,1,1,1,\dots\)

如果最终逆序对数都 \(\le 1\),有 \(n-1\) 种可能:\(0\) 的个数 \(1\sim n-1\)

回到问题,我们要枚举 \(m\),然后计数长度为 \(m\) 的第一次逆序对数 \(= 2\) 的序列种数。因为逆序对数 \(\le 1\) 的必然形如上面的形式,因此长度为 \(m\) 的第一次逆序对数 \(=2\) 的序列,在长度 \(m-1\) 时就是上面的形式,因此只需决策第 \(m\) 次的 \(1\) 插入哪里。如果中间那个 \(1\) 位于 \(a_j\),则有 \(j-1\) 种方案插入。因此对于序列 \(m\) 的方案数就是 \(\sum_{j=2}^{m-1}(j-1)=\dfrac{(m-2)(m-1)}{2} -1\)

总方案数即为 \(n-1+\sum_{m=3}^{n}(\dfrac{(m-2)(m-1)}{2}-1)\cdot dp[m]\)

posted @ 2024-11-24 10:23  FLY_lai  阅读(11)  评论(0编辑  收藏  举报