题目描述
输入描述
输出描述
输出一个整数,代表 K 倍区间的数目。
输入输出样例
示例
输入
5 2
1
2
3
4
5
输出
6
运行限制
- 最大运行时间:2s
- 最大运行内存: 256M
总通过次数: 8478 | 总提交次数: 12714 | 通过率: 66.7%
难度: 困难 标签: 2017, 暴力, 省赛
代码:
#include <stdio.h>
int cnt[100010]; // 定义一个数组 cnt,用于记录每种余数的出现次数
int main() {
int n, k;
scanf("%d%d", &n, &k); // 输入 n(数组长度)和 k(除数)
long long ans = 0; // ans 用于存储最终的结果,即满足条件的子数组个数
long long sum = 0; // sum 用于记录当前累计的子数组元素和的余数
cnt[0] = 1; // 初始化余数为 0 的个数为 1,表示初始状态下的累计和除以 k 的余数为 0
for (int i = 1; i <= n; i++) {
int a;
scanf("%d", &a); // 输入当前位置的数组元素 a
sum = (sum + a) % k; // 更新当前的累计和的余数
cnt[sum]++; // 记录当前余数的出现次数
}
// 计算满足条件的子数组个数
for (int i = 0; i < k; i++) {
ans += (long long) cnt[i] * (cnt[i] - 1) / 2; // 根据当前余数出现的次数计算满足条件的子数组个数
}
printf("%lld\n", ans); // 输出结果
return 0;
}
代码解释:
-
cnt 数组:用于记录每种余数的出现次数。数组大小为
100010
是为了确保能够存储所有可能的余数,即0
到k-1
。 -
输入部分:从标准输入读取数组长度
n
和除数k
。 -
累计和与余数计算:
sum
变量用于记录当前位置之前所有元素之和除以k
的余数。- 每次读取数组元素
a
后,更新sum
为(sum + a) % k
,以保持sum
在0
到k-1
的范围内。
-
cnt 数组更新:
cnt[sum]++
:每次更新当前余数的计数器,表示当前累计和的余数为sum
的个数增加了一个。
-
计算满足条件的子数组个数:
- 使用循环遍历所有可能的余数
0
到k-1
,计算满足条件的子数组个数。具体计算公式为cnt[i] * (cnt[i] - 1) / 2
,表示从cnt[i]
个元素中选取任意两个元素的组合数。
- 使用循环遍历所有可能的余数
-
输出结果:将最终计算得到的结果
ans
输出。