Lucas 定理
Lucas 定理
若 是质数,则对于任意整数 ,有:
例题 :序列统计
先求当一个序列长度为 时,元素大小都在 至 之间的单调不降元素的序列数量。
等价于把 个相同小球放入 个盒子里面,盒子可以为空。
常见思路:先把所有盒子里提前放一个小球,等价于把 个小球放入 个盒子里面,盒子不能为空。隔板,有 种方式。
现在把序列长度为 至 的方案数都求出来,答案为:
例题 :SP18878
题目大意
求杨辉三角第 行中偶数个数与奇数个数。
题目分析
我们先求第 行的奇数个数, 用这一行总数减一下就是偶数个数。
等价于求 。把 拆分成二进制数,二进制每一位记为 。
根据 Lucas 定理,
当 时, 那么所有的 必定满足 。
- 当 时,有 种情况:。
- 当 时,有 种情况: 或 。
等价于 为 的子集,故 二进制下若有 个 1,答案就为 。
例题 :Gift
很明显,任意一个 都有 。Lucas 显然了。
根据例题 2 的分析,等价于每一个 都是 的子集,根据题目条件,还要有 。
在值域上开 dp,没了。
#include <bits/stdc++.h>
using namespace std;
#define int long long
const int N = 3e5 + 5, mod = 1e9 + 7;
int n, a[N], dp[N], res;
signed main() {
cin >> n;
for (int i = 1; i <= n; i++) cin >> a[i];
for (int i = 0; i <= N - 5; i++) dp[i] = 1;
for (int i = 1; i <= n; i++) {
int t = a[i];
for (int j = t - 1 & t; j; j = j - 1 & t) dp[j] = (dp[j] + dp[t]) % mod; // trick:枚举子集
res += dp[t]; res %= mod;
}
cout << (res - n) % mod << endl;
}
例题 :P4345
根据 Lucas 定理:
容易发现 到 是相同的, 到 也是相同的,依次类推。所以可以对式子进行继续化简,提出相同的公因式。令 ,则有:
中括号那一堆和最开始求的东西形式一样,可以进行递归处理。复杂度 。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 地球OL攻略 —— 某应届生求职总结
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· 提示词工程——AI应用必不可少的技术
· .NET周刊【3月第1期 2025-03-02】