zoukankan      html  css  js  c++  java
  • [codeforces Mail.Ru Cup 2018 Round 3][B Divide Candies ][思维+数学]

    https://codeforces.com/contest/1056/problem/B

    题意:输入n,m    求((a*a)+(b*b))%m==0的(a,b)种数(1<=a,b<=n) (n<=1e9,m<=1000)

    题解:由于a,b的数量级很大,而m的数量级很小,又因为求((a*a)+(b*b))%m==0,即求((a%m*a%m)+(b%m*b%m))%m==0满足要求的a,b对数,也就是求a%m,b%m的平方分别取模后相加为0或者m的a,b对数,由于此时问题只和a%m平方取模的结果以及b%m平方取模的结果有关而且(a%m)和(b%m)为0~m-1的数,所以可以直接预处理出0~m-1数平方取模后的结果,然后直接通过计算1~n之间的数对m取模后得到相应(a%m)和(b%m)的个数,把相匹配的(a%m)和(b%m)的个数相乘即可.而求取模结果为x的个数就很容易了(P.S. 比赛的时候真的zz,求个数过程把大于等于写成等于..导致wa到怀疑人生...)

     1 #include<iostream>
     2 #include<cstdio>
     3 #include<cstring>
     4 #include<algorithm>
     5 #include<queue>
     6 #include<vector>
     7 #include<map>
     8 using namespace std;
     9 typedef  long long  ll;
    10 ll kk[1005];
    11 int main(){
    12  //freopen("in.txt","r",stdin);
    13         ll n,m;
    14         cin>>n>>m;
    15         vector<int>vc[1005];
    16         for(int i=0;i<m;i++){
    17                 vc[(i*i)%m].push_back(i);
    18                 kk[i]=(i*i)%m;
    19             }
    20         ll ans=0;
    21         for(int i=0;i<m;i++){
    22             for(int j=0;j<vc[(m-kk[i])%m].size();j++){
    23                     ans+=(n/m+((n%m>=i)&&i!=0))*(n/m+((n%m)>=(vc[(m-kk[i])%m][j]%m)&&vc[(m-kk[i])%m][j]!=0));
    24             }
    25         }
    26     cout << ans<<endl;
    27    
    28     return 0;
    29 }
  • 相关阅读:
    ssh登录
    wireless tools的使用
    Ubuntu中的minicom
    ubuntu 下交叉编译环境的搭建
    两个队列实现一个栈
    二叉树节点的插入
    二叉树的非递归遍历
    acwing 66. 两个链表的第一个公共结点
    acwing 60. 礼物的最大价值
    acwing 55. 连续子数组的最大和
  • 原文地址:https://www.cnblogs.com/MekakuCityActor/p/10019190.html
Copyright © 2011-2022 走看看