您的位置:首页 > 其它

POJ 2356 Find a multiple 【数学/抽屉原理】

2018-01-26 08:59 411 查看
题目大意:

给出N个自然数(正数),求解其中那些数字的和能够被N整除,并输出任意一组

方案:

【抽屉原理】    不是利用每个数字的抽屉原理,而是利用前缀和的抽屉定理

1.  N个前缀和,大部分情况肯定有两个前缀和,对于N的MOD一样,所以,这两个前缀和的差值,就是N的倍数

2.  当然遇见直接对N模0的特殊情况,需要直接输出该前缀和。因为前缀和要么重复,要么N个抽屉分居

关键代码:

const int maxn = 15000 + 10;
int a[maxn];
int sum[maxn];
int mod[maxn];
//key: 对应模MOD value: 第一次出现该MOD的下标
int n;
void init()
{
cin >> n;
for (int i = 0; i < n; i ++){
scanf("%d", &a[i]);
sum[i+1] += a[i] + sum[i];
}
}
void manage()
{
//从后往前扫描一遍
//遇见MOD == 0的前缀和,直接输出
//否则,将该前缀和压入MOD桶,待下次检查重复MOD
for (int i = 1; i <= n; i ++){
int check = sum[i]%n;
if (check == 0){
printf("%d\n", i);
for (int j = 0; j < i; j ++){
printf("%d\n", a[j]);
}
return ;
}
else {
if (mod[check]){
printf("%d\n", i-mod[check]);
for (int j = mod[check]; j < i; j ++){
printf("%d\n", a[j]);
}
return ; //注意位置
}
else {
mod[check] = i;
}
}
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  POJ