思路1:
线段树(982 ms)
每个点最多更新6次
代码:
#include<bits/stdc++.h>
using namespace std;
#define ll long long
#define pb push_back
#define ls rt<<1,l,m
#define rs rt<<1|1,m+1,r
#define mem(a,b) memset(a,b,sizeof(a)) const int N=1e6+;
const int INF=0x3f3f3f3f;
int a[N];
int d[N];
ll tree[N<<];
int mx[N<<];
void init(){
for(int i=;i<N;i++){
for(int j=i;j<N;j+=i)d[j]++;
}
}
void push_up(int rt){
mx[rt]=max(mx[rt<<],mx[rt<<|]);
tree[rt]=tree[rt<<]+tree[rt<<|];
}
void build(int rt,int l,int r){
if(l==r){
tree[rt]=mx[rt]=a[l];
return ;
}
int m=(l+r)>>;
build(ls);
build(rs);
push_up(rt);
}
void update(int L,int R,int rt,int l,int r){
if(mx[rt]<=)return ;
if(l==r){
tree[rt]=mx[rt]=d[tree[rt]];
return ;
}
int m=(l+r)>>;
if(L<=m)update(L,R,ls);
if(R>m)update(L,R,rs);
push_up(rt);
}
ll query(int L,int R,int rt,int l,int r){
if(L<=l&&r<=R)return tree[rt];
int m=(l+r)>>;
ll ans=;
if(L<=m)ans+=query(L,R,ls);
if(R>m)ans+=query(L,R,rs);
return ans;
}
int main(){
ios::sync_with_stdio(false);
cin.tie();
int n,m,t,l,r;
init();
cin>>n>>m;
for(int i=;i<=n;i++)cin>>a[i];
build(,,n);
while(m--){
cin>>t>>l>>r;
if(t==)update(l,r,,,n);
else cout<<query(l,r,,,n)<<endl;
}
return ;
}
思路2:
分块(1326 ms)
每个块最多更新6次
代码:
#include<bits/stdc++.h>
using namespace std;
#define ll long long
#define pb push_back
#define mem(a,b) memset(a,b,sizeof(a)) const int N=1e6+;
int d[N];
int a[N],belong[N],blo,flag[];
ll sum[];
void init(){
for(int i=;i<N;i++){
for(int j=i;j<N;j+=i)d[j]++;
}
}
void solve(int x){
if(flag[x])return ;
flag[x]=;
sum[x]=;
for(int i=(x-)*blo+;i<=x*blo;i++){
a[i]=d[a[i]];
sum[x]+=a[i];
if(a[i]>)flag[x]=;
}
}
void update(int l,int r){
if(belong[l]==belong[r]){
for(int i=l;i<=r;i++){
sum[belong[i]]-=a[i];
a[i]=d[a[i]];
sum[belong[i]]+=a[i];
}
return ;
}
for(int i=l;i<=belong[l]*blo;i++){
sum[belong[i]]-=a[i];
a[i]=d[a[i]];
sum[belong[i]]+=a[i];
}
for(int i=belong[l]+;i<=belong[r]-;i++)solve(i);
for(int i=(belong[r]-)*blo+;i<=r;i++){
sum[belong[i]]-=a[i];
a[i]=d[a[i]];
sum[belong[i]]+=a[i];
}
}
ll query(int l,int r){
ll ans=;
if(belong[l]==belong[r]){
for(int i=l;i<=r;i++)ans+=a[i];
return ans;
}
for(int i=l;i<=belong[l]*blo;i++)ans+=a[i];
for(int i=belong[l]+;i<=belong[r]-;i++)ans+=sum[i];
for(int i=(belong[r]-)*blo+;i<=r;i++)ans+=a[i];
return ans;
}
int main(){
ios::sync_with_stdio(false);
cin.tie();
init();
int n,m,t,l,r;
cin>>n>>m;
blo=sqrt(n);
for(int i=;i<=n;i++)cin>>a[i];
for(int i=;i<=n;i++){
belong[i]=(i-)/blo+;
sum[belong[i]]+=a[i];
}
while(m--){
cin>>t>>l>>r;
if(t==)update(l,r);
else cout<<query(l,r)<<endl;
}
return ;
}