您的位置:首页 > 其它

11105 - Semi-prime H-numbers(筛法)

2015-09-05 16:05 393 查看
该题新定义了一种H数,还有几个概念,要搞清楚:

1.H素数:本身不是1,不能写成两个不是1的H数才乘积。

2.H半素数:能写成2个H素数乘积的H数(注意,还得是H数)

这样我们就可以利用筛选法的思想,通过类似筛法求素数的方法筛出所有H素数。

细节参见代码:

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int INF = 1000000000;
const int maxn = 1000000+1;
int n,m,v,cnt=0,cur = 0,vis[maxn+5]={0},prime[maxn+5],a[maxn+5]={0};
void init() {
    cnt = 0;
    for(int i=1;(i*4+1)*(i*4+1)<=maxn;i++) if(!vis[i]) //类似筛法求素数  
       for(int j=i;(i*4+1)*(j*4+1)<=maxn;j++) 
            vis[4*i*j+i+j] = 1;  //意思就是4*(4*i*j+i+j)+1是H素数,暗含了它还是H数
    for(int i=1;i*4+1<=maxn;i++) {
        if(!vis[i]) prime[cnt++] = i*4+1;//保存H素数  
    }
    for(int i=0;i<cnt;i++) {
        if(prime[i]*prime[i]>maxn) break;//计算H半素数  
        for(int j=i;j<cnt;j++) {
            if(prime[i]*prime[j]>maxn) break;
            a[prime[i]*prime[j]] = 1;
        }
    }
    for(int i=1;i<=maxn;i++) a[i] += a[i-1];//打表记录答案  
}
int main() {
    init();
    while(~scanf("%d",&n)&&n) {
        printf("%d %d\n",n,a
);
    }
    return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: