题解:

莫比乌斯反演

再加上一个分块

然后和上一题差不多了

代码:

#include<cstdio>
#include<cmath>
#include<algorithm>
#include<cstring>
using namespace std;
typedef long long ll;
const int N=100005;
ll ans1,ans2;
int sum[N],a,b,x,y,z,tot,T,cnt,miu[N],flag[N],p[N];
void init()
{
    miu[1]=1;
    sum[1]=1;
    for (int i=2;i<N;i++)
     {
         if (!flag[i])
          {
              miu[i]=-1;
              p[++tot]=i;
          }
         for (int j=1;j<=tot;j++)
          {
              int k=p[j]*i;
              if (k>=N)break;
              flag[k]=1;
              if (i%p[j]==0)
               {
                   miu[k]=0;
                   break;
               }
              miu[k]-=miu[i];
          }
     }
    for (int i=1;i<N;i++)sum[i]=sum[i-1]+miu[i];     
}
ll find(int x,int y)
{
    if (x>y)swap(x,y);
    ll ans=0;int j;
    for (int i=1;i<=x;i=j+1)
     {
        j=min(x/(x/i),y/(y/i));
        ans+=(ll)(sum[j]-sum[i-1])*(x/i)*(y/i);
     }
    return ans; 
}
int main()
{
    scanf("%d",&T);
    init();
    while (T--)
     {
         ans1=ans2=0;
         scanf("%d%d%d%d%d",&a,&x,&b,&y,&z);
         x/=z;y/=z;a=(a-1)/z;b=(b-1)/z;
         ans1=find(x,y)-find(a,y)-find(x,b)+find(a,b);
         printf("%lld\n",ans1);
     }
}

 

posted on 2018-03-07 18:52  宣毅鸣  阅读(...)  评论(...编辑  收藏