「刷题记录」P2822 [NOIP2016 提高组] 组合数问题
本来以为很难,结果发现是道大水题
题目传送门:P2822 [NOIP2016 提高组] 组合数问题
思路:首先,你要知道什么是组合数,要知道组合数的递推公式 ,在本题中,你会发现 , 和 的范围都很小,所以我们可以直接暴力递推,但是可能会爆 long long我不知道,只是我的猜测,题中又提前给定了 ,所以我们可以在递推的过程中边推边 ,最后,只要模后是 ,就说明这个可以被 整除,如果在从头到尾扫一遍记录有多少个零,那你会得到 ,我们可以用前缀和优化,每行各记一个前缀和(为什么不直接二位前缀和?因为 ),上代码
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
inline ll read() {
ll x = 0;
int fg = 0;
char ch = getchar();
while (ch < '0' || ch > '9') {
fg |= (ch == '-');
ch = getchar();
}
while (ch >= '0' && ch <= '9') {
x = (x << 3) + (x << 1) + (ch ^ 48);
ch = getchar();
}
return fg ? ~x + 1 : x;
}
const int N = 2e3 + 10;
int T, k, n, m, cnt;
ll C[N][N], sum[N][N];
void pre() {
for (int i = 0; i <= 2001; ++ i) {
C[i][0] = 1;
for (int j = 1; j <= i; ++ j) {
C[i][j] = (C[i - 1][j - 1] + C[i - 1][j]) % k;
}
}
for (int i = 0; i <= 2001; ++ i) {
for (int j = 1; j <= i; ++ j) {
sum[i][j] += sum[i][j - 1];
sum[i][j] += (C[i][j] == 0);
}
}
}
int main() {
T = read(), k = read();
pre();
while (T --) {
n = read(), m = read();
ll ans = 0;
for (int i = 0; i <= n; ++ i) {
ans += sum[i][min(i, m)];
}
printf("%lld\n", ans);
}
return 0;
}
真的大水题
作者:yifan0305
出处:https://www.cnblogs.com/yifan0305/p/17026504.html
版权:本作品采用「署名-非商业性使用-相同方式共享 4.0 国际」许可协议进行许可。
转载时还请标明出处哟!
朝气蓬勃 后生可畏
分类:
刷题记录
Buy me a cup of coffee ☕.
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 单线程的Redis速度为什么快?
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 展开说说关于C#中ORM框架的用法!