CW高中-C0296D

发布时间 2023-12-08 07:44:15作者: Imcaigou

(下文所有出现的数均为整数)

LINK

一些细节比较难评,但整体是好题。

首先是题意比较难说,因为确实这个比较难懂,而且感觉描述得不是很清楚?

题意

题目给定了 \(n,m\)

首先有一个长度不固定(下文长度记为 \(L\))的数列 \(a\),且满足以下条件:

  • \(a_1 = 1\)
  • \(\begin{aligned}& \forall i \in [1,L): a_i = ka_{i-1} & k \in (1,m] \end{aligned}\)

然后你需要从中选出一些元素排列成一个新的数列 \(c\) (记其长度为 \(K\))(注意这里 \(c\) 中元素的相对顺序不一定要和 \(a\) 中这些元素对应位置的相对顺序一致),且满足以下条件:

  • \(\sum_{i=1}^K c_i = n\)
  • \(\forall i \in [1,K]: c_i | \sum_{j=1}^i c_j \Leftarrow \forall i \in [1,K]: c_i \mid \sum_{j=1}^{i-1} c_j\)
  • \(\exist i \in [1,K]: c_i=a_L\) (这里原题目好像说错惹)

要求对于每个可能的数列 \(a\) ,计算方案数并对这些方案数求和。

思路

根据 \(c\) 的限制 \(1\) 我们可知 \(a_L < n\),因此 \(L < \log_{2} n\)。(好耶)(然而并不重要)

我们先考虑如何对于一个固定的数列 \(a\) 以及其长度 \(L\) 如何求出对应的 \(c\) 的个数。

显然 \(a_1 = 1\) 。那么令 \(a_2 = t\)

所以 \(\forall i \in (1,t] : t \mid a_i\) ,根据 \(a\) 的限制 \(2\) 可知。

那么 \(c\) 中一定存在独立的 \(n \; \mathrm{mod} \; t\)\(a_1\) 。因为根据 \(c\) 的限制 \(1\) 和上一行说的性质,不含 \(a_1\)\(\sum c\) 的和一定是 \(t\) 的倍数,但 \(n\) 不一定是 \(t\) 的倍数,所以必须填这 \(n \; \mathrm{mod} \; t\)\(a_1\) 来满足 \(c\) 的限制 \(1\) ,即补 \(n\)。(当然若满足条件,还可以填更多的 \(a_1\) 进来)

再来观察这些 \(a_1\) 的位置。

发现用来补 \(n\)\(n \; \mathrm{mod} \; t\)\(a_1\) 一定在最后。因为若需要填这些数,则 \(t \nmid n\),如果把这些 \(a_1\) 随意地填在不靠后的位置,则 \(\exist i \in [1,K]: t \nmid \sum_{j=1}^i c_j,t \mid c_i \Rightarrow \exist i \in [1,K]: c_i \nmid \sum_{j=1}^i c_j\)。这个不满足 \(c\) 的限制 \(2\) ,所以寄了。所以 \(c\) 的后 \(n \; \mathrm{mod} \; t\) 个位置只能填 \(a_1\)

又发现其他 \(a_1\) 必须 \(t\) 个连成一个块一起出现,否则与限制冲突。那么不妨把这些连成一个块的 \(a_1\) 看作 \(a_2\) 的一种表示方法。然后相当于不再管 \(a_1\) ,而 \(a_2\) 多了一种表示方法(之后把这些块当作 \(a_2\) 考虑,与 \(a_1\) 不再有关)。又发现这时 \(\forall i \in [1,K],c_i \neq a_1 : t \mid c_i\) 。那么我们把 \(a_1\) 甩掉,再把所有 \(c\) 中的元素除以 \(t\),发现除了 \(a_2\) 多了种表示方式,\(n\) 变为 \(\lfloor \frac{n}{t} \rfloor\),其他与我们一开始考虑 \(a_1\) 时一样,这是我们把 \(a_2\) (已经除以 \(t\) 变成 \(1\))作为新的 \(a_1\)\(a_3\) 作为新的 \(a_2\),以此类推。

所以这时我们考虑递推,把考虑 \(a_2\) 的部分单独处理,再与 \(a_1\) 结合,就可以了。

所以我们有递推式 \(F(i,j)\) 表示这个部分中 \(n = i\)这个部分中 \(a_1\)\(j\) 种表示方法。

所以可以列出转移式:

\[F(i,j) = j^i - (j - 1)^i + \sum_{t=2}^{\min(m,i)} j^{i \, \mathrm{mod} \,t}F(\lfloor \frac{i}{t} \rfloor, j^t + 1) \]

解释一下:

\(j^i - (j-1)^i\) 表示如果直接以当前的 \(a_1\) 作为整体的 \(a_L\) 填入时的方案数(因为 \(a_L\) 是最后一个数,所以相当于是收尾),运用基础容斥(或许只是整体减局部?)用整体所有可行方案即 \(j^i\) 减去不含整体的 \(a_L\) 的方案数即 \((j-1)^i\)

然后在求和中枚举我们前文说的 \(a_2=t\),于是有刚刚说的 \(F(\lfloor \frac{i}{t} \rfloor, j^t + 1)\) 。然后还有就是 \(j^{i \, \mathrm{mod} \,t}\) 就是用 \(a_1\) 表示 \(a_2=t\) 的方案数,因为每一位上都可以填 \(j\) 种表示法,所以就很愉快可以直接这样算,要填的位就是前面说的 \(n \; \mathrm{mod} \; t\)

然后如果 \(t > n\) 就不能进入下一层继续递推,所以取了 \(\min\)

答案 \(Answer = F(n,1)\)。可以用记忆化搜索或 DP 实现。

时间复杂度分析

这个方法时间复杂度感觉会寄,然而没有(喜。

对于 \(i\) 分析,因为 \(\lfloor \frac{\lfloor \frac{n}{a} \rfloor}{b} \rfloor = \lfloor \frac{n}{ab} \rfloor\),所以所有 \(i\) 都会形如 \(\lfloor \frac{n}{j} \rfloor\),根据数论分块或关注反比例函数图像可知 \(i\)\(2\sqrt{n} - [\sqrt{n} \in \mathbb{N}]\) 种取值,其中 \([]\) 是艾弗森括号,相当于逻辑正伪转 \(10\) 的括号。所以 \(i\)\(\sqrt{n}\) 级别的。

对于 \(j\) 分析,因为模数 \(p=19\),而且 \(j\) 的相关计算都是作底数,所以 \(j\) 可以直接对 \(p\) 取模。

再算上内部枚举 \(t\) ,时间复杂度 \(O(pm\sqrt{n})\) 可以通过(喜。

因为这个复杂度已经 \(10^7\) 到极限了,所以内部一些比如快速幂之类的要用预处理+费马小定理解决,而记忆化搜索的 \(i\) 对应的记忆数组 \(f\) 的位置(排名)可以用数学方法算出来,就可以 \(O(1)\) 计算了,细节见部分代码。

Code

#define int long long
const int mod = 19;
int Qpow (int a, int p){
	if (a == 0 && p > 0)
		return 0;
	if (a == 0)
		return 1;
	p %= mod - 1;
	return pow19[a][p];
}
int F (int ni, int ci){
	int i;
	if (ni <= sqrtn)
		i = ni;
	else
		i = cnt - n / ni + 1;
	if (vis[i][ci])
		return f[i][ci];
	vis[i][ci] = true;
	(f[i][ci] = Qpow (ci, ni) - Qpow ((ci + mod - 1) % mod, ni) + mod) %= mod;
	for (int t = 2, j = ci * ci % mod;t <= m && t <= ni;++ t, (j *= ci) %= mod)
		(f[i][ci] += F (ni / t, (j + 1) % mod) * Qpow (ci, ni % t) % mod) %= mod;
	return f[i][ci];
}