当前位置: 代码迷 >> 综合 >> 筛-BZOJ-1607-[Usaco2008 Dec]Patting Heads 轻拍牛头
  详细解决方案

筛-BZOJ-1607-[Usaco2008 Dec]Patting Heads 轻拍牛头

热度:42   发布时间:2023-12-20 21:21:24.0

Description
今天是贝茜的生日,为了庆祝自己的生日,贝茜邀你来玩一个游戏.
贝茜让N(1≤N≤100000)头奶牛坐成一个圈.除了1号与N号奶牛外,i号奶牛与i-l号和i+l号奶牛相邻.N号奶牛与1号奶牛相邻.农夫约翰用很多纸条装满了一个桶,每一张包含了一个独一无二的1到1,000,000的数字.
接着每一头奶牛i从柄中取出一张纸条Ai.每头奶牛轮流走上一圈,同时拍打所有编号能整除在纸条上的数字的牛的头,然后做回到原来的位置.牛们希望你帮助他们确定,每一头奶牛需要拍打的牛.
Input
第1行包含一个整数N,接下来第2到N+1行每行包含一个整数Ai.
Output

第1到N行,每行的输出表示第i头奶牛要拍打的牛数量.

Sample Input
5 //有五个数,对于任一个数来说,其它的数有多少个是它的约数

2

1

2

3

4

INPUT DETAILS:

The 5 cows are given the numbers 2, 1, 2, 3, and 4, respectively.

Sample Output
2

0

2

1

3

OUTPUT DETAILS:

The first cow pats the second and third cows; the second cows pats no cows;

etc.


题解:
直接线性筛的思路,把out[i*k]都加上num[i],最后别忘记要记得减一(i本身自己那个一)。
我这里加了一个输入科技,kb菊苣的模板。


#include <iostream>
#include <cstdio>
#include <cstring>
#include <utility>
#include <cstdlib>
#include <algorithm>
#define MAXN 100005
#define MAX 1000005
using namespace std;
long long int num[MAX],a[MAXN],out[MAX],x=0,tmp,n;
template <class T>
inline bool scan_d(T &ret)
{char c;int sgn;if(c=getchar(),c==EOF) return 0; //EOFwhile(c!='-'&&(c<'0'||c>'9')) c=getchar();sgn=(c=='-')?-1:1;ret=(c=='-')?0:(c-'0');while(c=getchar(),c>='0'&&c<='9') ret=ret*10+(c-'0');ret*=sgn;return 1;
}
int main(int argc, const char * argv[])
{scan_d(n);for(long long int i=1; i<=n; i++){scan_d(a[i]);x=max(x,a[i]);num[a[i]]++;}for(long long int i=1; i<=x; i++){if(num[i])for(long long int j=i; j<=x; j+=i)out[j]+=num[i];}for(long long int i=1; i<=n; i++)printf("%lld\n",out[a[i]]-1);return 0;
}