思路
第一眼:纯模拟,但是数据太大会超时。仔细读题——当然这些数没必要两两不同
,有了 桶
的思想(其实也是筛子?)。
code
#include <cstdio>
#include <algorithm>
#include <iostream>
using namespace std;
const int N = 1e6 + 5;
int cow[N],cnt[N], ans[N];
int main()
{
int n, maxn = -1;
scanf("%d", &n);
for (int i = 1; i <= n; i++)
{
scanf("%d", &cow[i]);//记录每只牛的号码
cnt[cow[i]]++;//对应号码的“桶”++
maxn = max(maxn, cow[i]);//记录最大的数,节省后续时间
}
for (int i = 1; i <= maxn; i++)
if (cnt[i])//如果桶非空
{
//将所有因数包含此数(即此数的所有倍数)增加桶内所放牛的数目
for (int j = i; j <= maxn; j+=i)
ans[j] += cnt[i];
}
for (int i = 1; i <= n; i++)
printf("%d\n", ans[cow[i]] - 1);//自己也被加了,所以 -1
return 0;
}
错误示范
\(O(n^2)\) => 大数据会 \(TLE\)
#include <iostream>
#include <cstdio>
using namespace std;
const int N = 1e6 + 5;
int cow[N];
int cnt[N];
int main() {
int n;
scanf("%d", &n);
for (int i = 1; i <= n; i++) {
scanf("%d", &cow[i]);
}
for (int i = 1; i <= n; i++) {
for (int j = 1; j <= n; j++) {
if (i == j)
continue;
if (cow[i] % cow[j] == 0)
cnt[i]++;
}
}
for (int i = 1; i <= n; i++) {
printf("%d\n", cnt[i]);
}
return 0;
}