abc423 F - Loud Cicada

F - Loud Cicada

题意

给你 \(n\) 个数 \(a_i\),问有多少个 \(x \in [1,Y]\) 满足 \(a_i \mid x\)\(i\) 的个数等于 \(m\)

\(n ,m \le 20, a_i,Y \le 10^{18}\)

思路

\(a_i \mid x\)\(x\)\(\lfloor \frac{Y}{a_i} \rfloor\) 个。

显然可以枚举 \(i\) 的集合 \(S\),然后计算 \(\lfloor \frac{Y}{\text{lcm}(a_i ,i\in S)} \rfloor\)

然后算容斥系数。

容斥系数可以手推出来:

\(f_k\) 表示 \(|S| = k\) 的容斥系数。

假设 \(m=2\)

\(f_2 = 1\)

\(|S|=3\) 的方案应该总共被计算 \(0\) 次,现在已经被计算了 \(\binom{3}{2}\) 次,所以 \(f_3 = - \binom{3}{2}\)

\(|S|=4\) 的方案应该总共被计算 \(0\) 次,现在已经被计算了 \(\binom{4}{2} - \binom{3}{2} \binom{4}{3}\) 次,所以 \(f_4 = -\binom{4}{2} + \binom{3}{2} \binom{4}{3}\)

\(f_m=1, f_k = - \sum_{i=m}^{k-1} \binom{k}{i} f_i\)

于是就可以 \(O(2^n n + n^2)\) 做了。


注意,本段全是废话:

什么广义容斥原理、什么莫比乌斯变换,我完全看不懂啊,原来的定理如何证明和怎么运用到这题都不懂,有空必须学习一下,数学实在是太差了。

注意一些爆 long long 的问题。甚至会爆 __int128。我的解决方法是计算过程对一个大质数取模,因为最终答案显然 \(< Y\),所以是正确的吧(?。

注意上面这个是错的。

但是亲爱的,你告诉我,只 WA 一个 01-02.txt 是什么意思?

似乎在学术版看到了和我一样的做法。为啥直接用 __int128 是对的啊?

反正能过,就直接用 __int128 吧。


大神们都说这是二项式反演,我苦思冥想不能理解。那么我们使用二项式反演推一推。

唉,AI 还是太强了,就是理解能力有点奇怪。

\(f_k\) 表示恰好有 \(i\)\(a_i\)\(a_i\mid x\)\(x\) 的个数。

答案就是 \(f_m\)

但是 \(f_k\) 不好求。

\(g_k\) 表示满足至少有 \(k\)\(a_i\)\(a_i \mid x\)\(x\) 的个数。

\[g_i = \sum_{j\ge i} f_j \]

但是 \(g_k\) 也不好求。

\(h_k = \sum_{|S| = k} \lfloor \frac{Y}{\text{lcm}(a_i ,i\in S)} \rfloor\)。考虑 \(h_k\) 算重了多少。

一个有 \(c\)\(a_i \mid x\)\(x\) 会被算 \(\binom{c}{k}\) 次。

所以:

\[h_i = \sum_{j \ge i} \binom{j}{i} f_j \]

然后根据二项式反演,有;

\[f_i = \sum_{j \ge i} (-1)^{j-i} \binom{j}{i} h_j \]


证明二项式反演:

感谢 @CuteNess 的帮助!

\(F_S\) 表示恰好 \(i \in S, a_i \mid x\)\(x\) 的个数。

\(G_S\) 表示 \(\forall i \in S, a_i \mid x\)\(x\) 的个数。\(G_S = \lfloor \frac{Y}{\text{lcm}(a_i ,i\in S)} \rfloor\)

那么 \(G_S = \sum_{S \subseteq T} F_T\)

然后子集反演,得到 \(F_S = \sum_{S \subseteq T} (-1)^{|T|-|S|} G_T\)

\[\begin{aligned} f_k & = \sum_{|S| = k} F_S \\ & = \sum_{|S| = k} \sum_{S \subseteq T} (-1)^{|T|-|S|} G_T \\ \end{aligned} \]

\(h_j = \sum_{|S| = j} G_S\)

一个大小为 \(j\)\(T\) 就会被 \(\binom{j}{k}\)\(S\) 算到。

所以 \(f_k = \sum_{j \ge k} (-1)^{j-k} G_T\)

AI 的证明,太丑陋了!

理解二项式反演的推导,最好从「具体例子」入手,先观察规律,再上升到「组合恒等式」和「生成函数」的抽象证明。以下是分步推导思路,重点解释“为什么反演公式长这样”:

一、从具体例子找规律:n=2的情况

先看最简单的场景,设 \(n=2\),此时原关系式为:

\[\begin{cases} h_0 = \binom{0}{0}f_0 + \binom{1}{0}f_1 + \binom{2}{0}f_2 = f_0 + f_1 + f_2 \\ h_1 = \binom{1}{1}f_1 + \binom{2}{1}f_2 = f_1 + 2f_2 \\ h_2 = \binom{2}{2}f_2 = f_2 \end{cases}\]

我们的目标是\(h_i\) 反推 \(f_i\)。可以直接解方程组:

  • \(h_2 = f_2\),得 \(f_2 = h_2\)
  • 代入 \(h_1 = f_1 + 2f_2\),得 \(f_1 = h_1 - 2f_2 = h_1 - 2h_2\)
  • 代入 \(h_0 = f_0 + f_1 + f_2\),得 \(f_0 = h_0 - f_1 - f_2 = h_0 - (h_1 - 2h_2) - h_2 = h_0 - h_1 + h_2\)

观察结果,发现规律:

\[\begin{cases} f_2 = h_2 \\ f_1 = h_1 - 2h_2 = \binom{1}{1}h_1 - \binom{2}{1}h_2 \\ f_0 = h_0 - h_1 + h_2 = \binom{0}{0}h_0 - \binom{1}{0}h_1 + \binom{2}{0}h_2 \end{cases}\]

每一项的系数都是 \((-1)^{j-i}\binom{j}{i}\)(例如 \(f_0\)\(h_2\) 的系数是 \((-1)^{2-0}\binom{2}{0}=1\))。

二、n=3验证:规律是否一致?

原关系式:

\[\begin{cases} h_0 = f_0 + f_1 + f_2 + f_3 \\ h_1 = f_1 + 2f_2 + 3f_3 \\ h_2 = f_2 + 3f_3 \\ h_3 = f_3 \end{cases}\]

解方程组:

  • \(f_3 = h_3\)
  • \(f_2 = h_2 - 3f_3 = h_2 - 3h_3\)
  • \(f_1 = h_1 - 2f_2 - 3f_3 = h_1 - 2(h_2 - 3h_3) - 3h_3 = h_1 - 2h_2 + 3h_3\)
  • \(f_0 = h_0 - f_1 - f_2 - f_3 = h_0 - (h_1 - 2h_2 + 3h_3) - (h_2 - 3h_3) - h_3 = h_0 - h_1 + h_2 - h_3\)

结果完全符合规律:

\[f_i = \sum_{j=i}^3 (-1)^{j-i}\binom{j}{i}h_j \]

例如 \(f_1 = \binom{1}{1}h_1 - \binom{2}{1}h_2 + \binom{3}{1}h_3 = h_1 - 2h_2 + 3h_3\)

三、核心问题:为什么是 \((-1)^{j-i}\binom{j}{i}\)

从例子中可见,反演的关键是用交错符号(正负交替)抵消原关系式中“重复计算”的部分

原关系式 \(h_i = \sum_{j≥i}\binom{j}{i}f_j\) 的本质是:\(f_j\) 会被所有 \(i≤j\)\(h_i\) 计数 \(\binom{j}{i}\) 次(例如 \(f_3\)\(h_1\) 中被计 \(\binom{3}{1}=3\) 次,在 \(h_2\) 中被计 \(\binom{3}{2}=3\) 次)。

反演需要“剥离”这些重复计数,而 \((-1)^{j-i}\) 的作用正是正负抵消

  • \(j=i\) 时,只有 \(h_i\) 包含 \(f_i\),系数为正(\(\binom{i}{i}=1\));
  • \(j>i\) 时,\(f_j\)\(h_i\) 中被多计的部分,会被 \(h_{i+1},...,h_j\) 中的负系数抵消。

四、严格证明:利用组合恒等式

要证明对任意 \(i≤n\),有:

\[f_i = \sum_{j=i}^n (-1)^{j-i}\binom{j}{i}h_j \]

只需将原关系式 \(h_j = \sum_{k=j}^n \binom{k}{j}f_k\) 代入右边,验证结果等于 \(f_i\)

右边 \(= \sum_{j=i}^n (-1)^{j-i}\binom{j}{i} \cdot \sum_{k=j}^n \binom{k}{j}f_k\)
\(= \sum_{k=i}^n f_k \sum_{j=i}^k (-1)^{j-i}\binom{j}{i}\binom{k}{j}\) (交换求和顺序,\(k≥j≥i\)

核心是证明内层和 \(\sum_{j=i}^k (-1)^{j-i}\binom{j}{i}\binom{k}{j} = \delta_{i,k}\)(克罗内克符号:\(i=k\) 时为 1,否则为 0)。

化简内层和:

利用组合恒等式 \(\binom{j}{i}\binom{k}{j} = \binom{k}{i}\binom{k-i}{j-i}\)(从 \(k\) 中选 \(j\) 再选 \(i\),等价于先选 \(i\) 再从剩余 \(k-i\) 中选 \(j-i\))。

\(t = j - i\)(则 \(t≥0\)\(k-i≥t\)),内层和变为:
\(\sum_{t=0}^{k-i} (-1)^t \binom{k}{i}\binom{k-i}{t} = \binom{k}{i} \sum_{t=0}^{k-i} (-1)^t \binom{k-i}{t}\)

根据二项式定理,\(\sum_{t=0}^m (-1)^t \binom{m}{t} = (1-1)^m = 0^m\)\(m≥1\) 时为 0,\(m=0\) 时为 1)。

因此:

  • \(k = i\) 时,\(m = k-i = 0\),和为 \(\binom{i}{i} \cdot 1 = 1\)
  • \(k > i\) 时,\(m = k-i ≥1\),和为 \(\binom{k}{i} \cdot 0 = 0\)

即内层和 \(= \delta_{i,k}\),因此右边 \(= \sum_{k=i}^n f_k \cdot \delta_{i,k} = f_i\),证明成立。

五、总结:理解反演的3个关键

  1. 直观来源:从低维例子(n=2,3)观察到反演系数的规律(交错符号+组合数);
  2. 核心作用\((-1)^{j-i}\) 抵消原关系式中 \(f_j\) 被重复计数的部分;
  3. 严格基础:依赖组合恒等式 \(\sum_{t=0}^m (-1)^t \binom{m}{t} = 0^m\),这是二项式定理的直接结果。

结合计数问题(如“至少”与“恰好”的转换)理解会更深刻:反演本质是“修正重复计数”的数学工具。

code

#include<bits/stdc++.h>
#define sf scanf
#define pf printf
#define rep(x,y,z) for(int x=y;x<=z;x++)
#define per(x,y,z) for(int x=y;x>=z;x--)
using namespace std;
typedef long long ll;
typedef __int128 lll;
namespace wing_heart {
	constexpr int N=21;
	int n,m;
	ll a[N],s;
	ll gcd(ll a,ll b) { return b ? gcd(b,a%b) : a; }
	ll getlcm(int t) {
		lll p=1;
		rep(i,1,n) if((t>>(i-1))&1) {
			p=(lll)p*a[i]/gcd(p,a[i]);
			if(p>s) return -1; 
		}
		return p;
	}
	lll ans;
	ll c[N][N];
    void main() {
		sf("%d%d%lld",&n,&m,&s);
		rep(i,1,n) sf("%lld",&a[i]);
		c[0][0]=1;
		rep(i,1,n) {
			c[i][0]=1;
			rep(j,1,i) c[i][j]=c[i-1][j-1]+c[i-1][j];
		}
		rep(i,1,(1<<n)-1) {
			int k=__builtin_popcount(i);
			if(k<m) continue;
			ll lcm=getlcm(i);
			if(lcm==-1) continue;
			ll op = (k-m)&1 ? -1 : 1;
			ans+=(lll)op*c[k][m]*(s/lcm);
		}
		pf("%lld\n",(ll)ans);
    }
}
int main() {
    #ifdef LOCAL
    freopen("in.txt","r",stdin);
    freopen("my.out","w",stdout);
    #endif
    wing_heart :: main();
}
posted @ 2025-09-15 17:17  wing_heart  阅读(80)  评论(4)    收藏  举报