ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

2021ICPC预选赛第二场——L Euler Function

2021-10-01 09:35:25  阅读:236  来源: 互联网

标签:Function rt phi int 2021ICPC tag mul Euler mod


思路:线段树区间乘法,维护$\phi(x_i)$,每次update w的质因子。

几个性质:

  1. 当$m$与$n$互质时有$\phi(m*n)==\phi(m)*\phi(n)$(这时使用单点修改)
  2. 当$k$是一个质数时,$\phi(k)==k-1$(这个代码里没有用到,但可以便于打表)
  3. $w$是一个质数,此时如果$\gcd(w,x_i)==w$则$\phi(w*x_i)==w*\phi(x_i)$。(如果一个区间里的$x_i$都满足这一点,可以区间修改)
  1 #include<cstdio>
  2 #include<algorithm>
  3 #include<cmath>
  4 #include<cstring>
  5 #include<queue>
  6 #include<cstdlib>
  7 using namespace std;
  8 
  9 #define mxp 114 //最大需要处理的数字
 10 #define ll long long
 11 #define rep(i,l,r) for(int i=l;i<=r;++i)
 12 #define drep(i,r,l) for(int i=r;i>=l;--i)
 13 #define maxn 114514
 14 #define lson rt<<1
 15 #define rson rt<<1|1
 16 inline char nc(){
 17     static char buf[100010],*p1=buf,*p2=buf;
 18     return p1==p2&&(p2=(p1=buf)+fread(buf,1,100000,stdin),p1==p2)?EOF:*p1++;
 19 }
 20 #ifndef ONLINE_JUDGE
 21 #define nc() getchar()
 22 #endif
 23 inline int read(){
 24     int x=0,y=1;
 25     char ch=nc();
 26     while(ch<'0'||ch>'9'){
 27         if(ch=='-')y=-y;
 28         ch=nc();
 29     }
 30     while(ch>='0'&&ch<='9'){
 31         x=10*x+(ch^48);
 32         ch=nc();
 33     }
 34     return x*y;
 35 }
 36 int n,m,cnt;
 37 ll phi[255];
 38 const ll mod=998244353;
 39 ll tr_phi[maxn<<2];//欧拉函数之和
 40 ll seq[maxn];
 41 ll tag_mul[maxn<<2];
 42 bool isNP[514];
 43 ll prime[514];
 44 bool MUL[maxn<<2][514];
 45 inline void getprime(int x){
 46     rep(i,2,x){
 47         if(!isNP[i])prime[++cnt]=i;
 48         rep(j,1,cnt){
 49             if(i*prime[j]>x)break;
 50             isNP[i*prime[j]]=1;
 51             if(i%prime[j]==0)break;
 52         }
 53     }
 54 }
 55 void pushdown(int l,int r,int rt){
 56     int mid=(l+r)>>1;
 57     if(tag_mul[rt]!=1){
 58         tr_phi[lson]*=tag_mul[rt];
 59         tr_phi[lson]%=mod;
 60         tr_phi[rson]*=tag_mul[rt];
 61         tr_phi[rson]%=mod;
 62         tag_mul[lson]*=tag_mul[rt];
 63         tag_mul[lson]%=mod;
 64         tag_mul[rson]*=tag_mul[rt];
 65         tag_mul[rson]%=mod;
 66         tag_mul[rt]=1;
 67     }
 68     return;
 69 }
 70 void pushup(int rt){
 71     tr_phi[rt]=(tr_phi[lson]%mod+tr_phi[rson]%mod)%mod;
 72     rep(i,2,mxp){
 73         MUL[rt][i]=MUL[lson][i]&MUL[rson][i];
 74     }
 75 }
 76 void build(int l,int r,int rt){
 77     tag_mul[rt]=1;
 78     if(l==r){
 79         int dt=seq[l];
 80         tr_phi[rt]=phi[dt];
 81         rep(i,1,cnt){
 82             int cur_pm=prime[i];
 83             if(dt%cur_pm==0){
 84                 MUL[rt][cur_pm]=1;
 85             }
 86         }
 87         return;
 88     }
 89     int mid=(l+r)>>1;
 90     build(l,mid,lson);
 91     build(mid+1,r,rson);
 92     pushup(rt);
 93 }
 94 void update(int L,int R,int l,int r,int rt,ll w){//这个更新的w只考虑质因子。
 95     if(L<=l&&R>=r&&MUL[rt][w]){   
 96         tr_phi[rt]*=w;
 97         tag_mul[rt]*=w;
 98         tr_phi[rt]%=mod;
 99         tag_mul[rt]%=mod;
100         return;
101     }
102     if(l==r){
103         tr_phi[rt]*=phi[w];
104         tr_phi[rt]%=mod;
105         tag_mul[rt]=1;
106         MUL[rt][w]=1;
107         return;
108     }
109     pushdown(l,r,rt);
110     int mid=(l+r)>>1;
111     if(L<=mid)update(L,R,l,mid,lson,w);
112     if(mid+1<=R)update(L,R,mid+1,r,rson,w);
113     pushup(rt);
114 }
115 ll query(int L,int R,int l,int r,int rt){
116     if(r<L||l>R)return 0;
117     if(L<=l&&r<=R)return tr_phi[rt];
118     pushdown(l,r,rt);
119     int mid=(l+r)>>1;
120     return (query(L,R,l,mid,lson)%mod+query(L,R,mid+1,r,rson)%mod)%mod;
121 }
122 inline void getphi(int x){
123     phi[0]=0,phi[1]=1;
124     rep(i,2,x)phi[i]=i;
125     rep(i,2,x){
126         if(phi[i]==i){
127             for(int j=i;j<=x;j+=i){
128                 phi[j]=phi[j]/i*(i-1);
129             }
130         }
131     }
132 }
133 int main(){
134     getphi(125);
135     getprime(125);
136     n=read(),m=read();
137     rep(i,1,n){
138         seq[i]=read();
139     }
140     build(1,n,1);bool flag=1;
141     rep(i,1,m){
142         int op=read(),x=read(),y=read();
143         
144         if(op==1){
145             flag? printf("%lld",query(x,y,1,n,1)),flag=0:printf("\n%lld",query(x,y,1,n,1));
146         }
147         else if(op==0){
148             ll up=read();
149             int cur=1;
150             while(cur<=cnt){
151                 ll cur_p=prime[cur];
152                 while(up%cur_p==0){
153                     update(x,y,1,n,1,cur_p);
154                     up/=cur_p;    
155                 }
156                 if(up==1)break;
157                 ++cur;
158             }
159         }
160     }
161     return 0;
162 }
View Code

 

标签:Function,rt,phi,int,2021ICPC,tag,mul,Euler,mod
来源: https://www.cnblogs.com/tzzzzzzzx/p/15358716.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有