zoukankan      html  css  js  c++  java
  • BZOJ3853: GCD Array

    题目:http://www.lydsy.com/JudgeOnline/problem.php?id=3853

    题解:我们发现直接修改是肯定不行的。因为一次有可能修改的很多。而且编号也是不连续的。

    搬运题解:

    {

    注意到给所有gcd(x,n)==d的数加上v等价于给每个数加上[gcd(x,n)==d]*v,而我们可以发现:

    [gcd(x,n)==d]*v => 

    [gcd(x/d,n/d)==1] *v=> 

    sigma(mu[q] * v) (q | n/d && q | x/d)

    => sigma(mu[q] * v) (q | n/d && q*d | x)  

     其中mu是莫比乌斯函数

    我们可以构造一个数组f,让a[i] == sigma(f[j]) (j | i),然后修改操作就变成了:对所有满足条件的q,让f[q*d]加上mu[q] * v,那么根据f数组的性质,我们每个a[i]就能很顺利的加上[gcd(x,n)==d]*v了。

    }

    其实这相当与我们把修改和查询都往前推了一下,推到了一个公共的部分,然后发现这个部分维护所需时间在允许范围内。so。。。

    这题的思想还需要领悟。。。

    代码:

      1 #include<cstdio>
      2 
      3 #include<cstdlib>
      4 
      5 #include<cmath>
      6 
      7 #include<cstring>
      8 
      9 #include<algorithm>
     10 
     11 #include<iostream>
     12 
     13 #include<vector>
     14 
     15 #include<map>
     16 
     17 #include<set>
     18 
     19 #include<queue>
     20 
     21 #include<string>
     22 
     23 #define inf 1000000000
     24 
     25 #define maxn 200000
     26 
     27 #define maxm 200000+5
     28 
     29 #define eps 1e-10
     30 
     31 #define ll long long
     32 
     33 #define pa pair<int,int>
     34 
     35 #define for0(i,n) for(int i=0;i<=(n);i++)
     36 
     37 #define for1(i,n) for(int i=1;i<=(n);i++)
     38 
     39 #define for2(i,x,y) for(int i=(x);i<=(y);i++)
     40 
     41 #define for3(i,x,y) for(int i=(x);i>=(y);i--)
     42 
     43 #define for4(i,x) for(int i=head[x],y=e[i].go;i;i=e[i].next,y=e[i].go)
     44 
     45 #define for5(n,m) for(int i=1;i<=n;i++)for(int j=1;j<=m;j++)
     46 
     47 #define mod 1000000007
     48 
     49 using namespace std;
     50 
     51 inline int read()
     52 
     53 {
     54 
     55     int x=0,f=1;char ch=getchar();
     56 
     57     while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
     58 
     59     while(ch>='0'&&ch<='9'){x=10*x+ch-'0';ch=getchar();}
     60 
     61     return x*f;
     62 
     63 }
     64 int n,m,mu[maxn+1],p[maxn],tot;
     65 ll s[maxn];
     66 bool v[maxn+1];
     67 vector<int>fac[maxn+1];
     68 inline void add(int x,int y)
     69 {
     70     for(;x<=n;x+=x&(-x))s[x]+=y;
     71 }
     72 inline ll sum(int x)
     73 {
     74     ll t=0;
     75     for(;x;x-=x&(-x))t+=s[x];
     76     return t;
     77 }
     78 inline void get()
     79 {
     80     mu[1]=1;
     81     for2(i,2,maxn)
     82     {
     83         if(!v[i])p[++tot]=i,mu[i]=-1;
     84         for1(j,tot)
     85         {
     86             int k=i*p[j];
     87             if(k>maxn)break;
     88             v[k]=1;
     89             if(i%p[j])mu[k]=-mu[i];
     90             else {mu[k]=0;break;}
     91         }
     92         //cout<<i<<' '<<mu[i]<<endl;
     93     }
     94     for1(i,maxn)
     95      for(int j=i;j<=maxn;j+=i)
     96       fac[j].push_back(i);
     97 }
     98 
     99 int main()
    100 
    101 {
    102 
    103     freopen("input.txt","r",stdin);
    104 
    105     freopen("output.txt","w",stdout);
    106     get();
    107 
    108     for1(cs,inf)
    109     {
    110         n=read();m=read();
    111         if(!n&&!m)break;
    112         printf("Case #%d:
    ",cs);
    113         memset(s,0,sizeof(s));
    114         while(m--)
    115         {
    116             int op=read();
    117             if(op==1)
    118             {
    119                 int x=read(),y=read(),z=read();
    120                 if(x%y)continue;
    121                 x/=y;
    122                 for3(i,fac[x].size()-1,0)add(fac[x][i]*y,mu[fac[x][i]]*z);
    123             }else
    124             {
    125                 int t=read();ll ans=0;
    126                 for(int i=1,j;i<=t;i=j+1)
    127                 {
    128                     j=t/(t/i);
    129                     ans+=(ll)t/i*(sum(j)-sum(i-1));
    130                 }
    131                 printf("%lld
    ",ans);
    132             }
    133         }
    134     }
    135 
    136     return 0;
    137 
    138 }  
    View Code

     

     

  • 相关阅读:
    Linux C编程 GCC的使用
    51nod 1079 中国剩余定理
    51nod 1074 约瑟夫环 V2
    51nod 1073 约瑟夫环
    51nod 1072 威佐夫游戏
    ACM博弈论总结
    51nod 1069 Nim游戏
    2017 ACM-ICPC 亚洲区(南宁赛区)网络赛 The Heaviest Non-decreasing Subsequence Problem
    2017 ACM-ICPC 亚洲区(南宁赛区)网络赛 Overlapping Rectangles
    2017 ACM-ICPC 亚洲区(南宁赛区)网络赛 Minimum Distance in a Star Graph
  • 原文地址:https://www.cnblogs.com/zyfzyf/p/4250977.html
Copyright © 2011-2022 走看看