code vs guard 的无聊

来源:互联网 发布:政府财政支出数据 编辑:程序博客网 时间:2024/05/01 08:52

1279 Guard 的无聊

 时间限制: 1 s
 空间限制: 128000 KB
 题目等级 : 黄金 Gold
题目描述 Description

在那楼梯那边数实里面,有一只 guard,他活泼又聪明,他卖萌又霸气。他每天刷题虐 场 D 人考上了 PKU,如果无聊就去数一数质数~~ 有一天 guard 在纸上写下了一串数字,他发现数出每个数有多少个质因子是非常有(wu) 趣(liao)的事情,于是快乐的开始了数质因子之旅。现在他有一个更有(wu)趣(liao)的想法, 他想知道第a个数到第b个数每个数的质因子个数之和。更有趣的是,他一共写下了200 万个数字哟。由于guard是神犇所以不屑于求如此简单的问题,现在他把问题交给了Mr.shu, 但是他不会…,如果你能回答他的问题就能获得 guard 的亲笔签名哦~~。

输入描述 Input Description

第一行 1 个数 n,表示 guard 写下了 n 个数。 第二行 n 个用空格隔开的数,表示 guard 写下的 n 个数(每个数都不大于 10000,不小 于 1)。 第三行 1 个数 m,表示 guard 的询问数。 接下来 m 行,每行一个 a 和 b,表示 guard 想知道 a 到 b(包括 a 和 b)的每个数的质 因子个数之和。

输出描述 Output Description

一共 m 行。每行一个数表示对每个询问的答案。

样例输入 Sample Input
5 4 2 1 6 30 2 1 3 2 5 
样例输出 Sample Output
36
数据范围及提示 Data Size & Hint

【输入输出样例说明】

 

4=2*2 有 2 个不同质因子,2 有 1 个,1 有 0 个,6 有 2 个,30 有 3 个,

 

所以[1,3]有 2+1+0 个,[2,5]有 1+0+2+3 个。

 

【数据范围】

 

20%的数据满足 n<=1000,m<=10

 

50%的数据满足 n<=10000

 

100%的数据满足 n<=2000000,m<=100000




#include<iostream>#include<cstdio>#include<cstring>using namespace std;int num[2000003],ans[2000003],tree[20000003];int n,m,i,j,maxn,head,tail;int zhishu[100003],b[10000],p,flag[10003];int queue[100003],step[100003];void chuli(){    zhishu[1]=1; for (int i=2;i<=10000;i++) if (zhishu[i]==0)  {  for (int j=i+i;j<=10000;j+=i)   zhishu[j]=1;  }for (int i=2;i<=10000;i++) if (zhishu[i]==0)  p++,b[p]=i; }void build(int now,int l,int r){if (l==r) { tree[now]=ans[l]; return; }int mid=(l+r)/2;build(now<<1,l,mid);build((now<<1)+1,mid+1,r);tree[now]=tree[now<<1]+tree[(now<<1)+1];}int qsum(int now,int l,int r,int ll,int rr){if (ll<=l&&rr>=r) { return tree[now]; }int mid=(l+r)/2;int ans=0;if (ll<=mid) ans+=qsum(now<<1,l,mid,ll,rr);if (rr>mid) ans+=qsum((now<<1)+1,mid+1,r,ll,rr);return ans;}int main(){scanf("%d",&n);for(i=1;i<=n;i++) { scanf("%d",&num[i]); maxn=max(maxn,num[i]); }chuli();tail++; step[1]=0; queue[tail]=1; flag[1]=1;while (head<tail) { head++; int x=queue[head]; for (i=1;i<=1229;i++)  {  if (x*b[i]>maxn) break;  if ((x*b[i])<=maxn&&flag[x*b[i]]==0)  {     step[x*b[i]]=step[x]+1;flag[x*b[i]]=1;tail++;  queue[tail]=x*b[i];  }     } }for (i=1;i<=n;i++) ans[i]=step[num[i]];build(1,1,n);scanf("%d",&m);for (i=1;i<=m;i++) { int x,y; scanf("%d%d",&x,&y); printf("%d\n",qsum(1,1,n,x,y)); }} 
质因数分解+线段树

0 0
原创粉丝点击