ACM: 数论题 toj 1721
2016-05-19 23:19
429 查看
Partial Sums
描述
Given a series of n
numbers a1, a2, ..., an, the partial sum of the numbers is defined
as the sum of ai, ai+1, ..., aj.
You are supposed to calculate how many partial sums of a given
series of numbers could be divided evenly by a given number
m.
输入
There are multiple test,
each contains 2 lines.
The first line is 2 positive integers n (n <= 10000
) and m (m <= 5000).
The second line contains n non-negative integers a1, a2, ..., an.
Numbers are separated by one or several spaces.
The input is ended by EOF.
输出
One test each line - the
number of partial sums which could be divided by m.
样例输入
5 4
1 2 3 4 5
6 7
9 8 7 6 5 4
样例输出
2
3
题意: 求出子序和能够整除m的子序个数.
解题思路:
1. sum[i....j] = sum[1.....j] -
sum[1.....(i-1)] <
== > sum[1...j] % m == sum[1...(n-1)] % m
2. 显然, 它们的求余相同时, 表示即前段相同, 剩下的序列和是可以整除m.
3. 例如:
5 4
1 2 3 4 5
(1+2) % 4 = 3
(1+2+3+4+5) % 4 = 3
sum[0...4] - sum[0...1] = (3+4+5)
% 4 = 0
4. 所以在余数相同的情况下,
任意选取两个从1开始的序列和相减, 得到中间序列和必须
整除m. (个数: 从个数中选取2个.
C几2).
代码:
#include
<cstdio>
#include <iostream>
#include <cstring>
using namespace std;
#define MAX 10005
int ca[MAX];
int n, m;
int t;
int sum;
int main()
{
// freopen("input.txt","r",stdin);
int i, j;
int result;
while(scanf("%d
%d",&n,&m) != EOF)
{
memset(ca,0,sizeof(ca));
result = 0;
sum = 0;
for(i = 0; i <
n; ++i)
{
scanf("%d",&t);
sum = (sum +
t) % m;
if(sum == 0)
result++;
ca[sum]++;
}
for(i = 0; i
< m; ++i)
{
if(ca[i] !=
0)
result
+= ca[i] * (ca[i] - 1) / 2;
}
printf("%d\n",result);
}
return 0;
}
相关文章推荐
- ACM: 序列中找最小逆序对 杂题 TOJ…
- mapReduce概念及用法
- ACM: 简单最小生成树 图论题 poj 1…
- ACM: spfa+dfs 图论题 poj 2679
- 图论: 最大流
- ACM: 最大流 图论题 poj 1797
- 线程的常用方法
- ACM: 差分约束 图论题 poj 2983 sp…
- ACM: 二分图最大匹配 hdu 2063
- 数据
- ACM: 二分法 数论题 poj 1905
- ZOJ的轻松ACMER语录.. 狗一样的学…
- ACM: spfa求解 图论题 (对差分约束…
- ACM: 最小费用用最大流 图论题 poj…
- ACM: K次最小费用最大流 图论题 po…
- ACM: 哈希暴力求解 哈希题 poj 184…
- ACM: 最小费用最大流 图论题 poj 2…
- 理解并解决GBK转UTF-8奇数中文乱码(转)
- HDU 2098 分拆素数和
- ACM: hash题 poj 2503