zoukankan      html  css  js  c++  java
  • ZOJ 3673

    思路:要求满足的m=a3+b3=(a+b)(a2-ab+b2)的(a,b)组合。

    令t=a+b,则t一定是m的约数,所以应枚举m的所有约数。

    然后可以得到

    a+b=t

    ab=(t2-m/t)/3=p

    继而转化为a2-ta+p=0是否有正整数解就可以了。

    再就是注意范围要用unsigned long long。

    代码:

      1 #include<cstdio>
      2 #include<cmath>
      3 #include<algorithm>
      4 #include<iostream>
      5 #define ll unsigned long long
      6 #define M 5000001
      7 #define mm 2641636
      8 using namespace std;
      9 int cnt,num,cn;
     10 ll prime[M],p[100],e[100];
     11 bool f[M];
     12 ll n;
     13 struct point
     14 {
     15     ll a,b;
     16     bool operator<(const point &aa) const
     17     {
     18         return a<aa.a;
     19     }
     20 }an[1000];
     21 void init()
     22 {
     23     cnt=0;
     24     for(int i=2;i<M;i++){
     25         if(!f[i]) prime[cnt++]=i;
     26         for(int j=0;j<cnt&&i*prime[j]<M;j++){
     27             f[i*prime[j]]=1;
     28             if(i%prime[j]==0) break;
     29         }
     30     }
     31 }
     32 void fac(ll m)
     33 {
     34     num=0;
     35     for(ll i=0;i<cnt&&(ll)prime[i]*prime[i]<=m;i++){
     36         if(m%prime[i]==0){
     37             p[num]=prime[i];
     38             ll j=1;
     39             m/=prime[i];
     40             while(m%prime[i]==0){
     41                 j++;
     42                 m/=prime[i];
     43             }
     44             e[num++]=j;
     45         }
     46     }
     47     if(m>1){
     48         p[num]=m;
     49         e[num++]=1;
     50     }
     51 }
     52 ll ispw2(ll a)
     53 {
     54     ll b=sqrt(1.0*a);
     55     if((ll)b*b==a) return b;
     56 //    if((ll)(b+1)*(b+1)==a) return b+1;
     57     return M;
     58 }
     59 bool IS(ll a,ll b)
     60 {
     61     for(int i=0;i<cn;i++)
     62         if(an[i].a==a&&an[i].b==b) return 1;
     63     return 0;
     64 }
     65 void is(ll t)
     66 {
     67     ll x1,x2;
     68     ll p=n/t;
     69     ll a=t*t-p;
     70     if(a>0&&a%3!=0) return ;
     71     ll m=a/3;
     72 //    cout<<t<<' '<<m<<endl;
     73     ll b=t*t-4*m;
     74     if(b<0) return ;
     75     ll c=ispw2(b);
     76     if(c==M) return ;
     77     if((t+c)%2==0){
     78         x1=(t+c)/2;
     79         x2=t-x1;
     80         if(x1>x2) swap(x1,x2);
     81         if(x1>0&&x1<t&&x1<mm&&x2<mm&&x2>0&&x2<t&&!IS(x1,x2)){
     82             an[cn].a=x1;
     83             an[cn++].b=x2;
     84         }
     85     }
     86     if(t-c>0&&(t-c)%2==0){
     87         x1=(t-c)/2;
     88         x2=t-x1;
     89         if(x1>x2) swap(x1,x2);
     90         if(x1>0&&x1<t&&x1<mm&&x2<mm&&x2>0&&x2<t&&!IS(x1,x2)){
     91             an[cn].a=x1;
     92             an[cn++].b=x2;
     93         }
     94     }
     95 //    cout<<t<<endl;
     96 }
     97 ll pw(ll a,ll b)
     98 {
     99     ll ans=1;
    100     while(b){
    101         if(b&1) ans*=a;
    102         b>>=1;
    103         a*=a;
    104     }
    105     return ans;
    106 }
    107 void dfs(int m,ll s)
    108 {
    109     is(s);
    110     if(m>=num) return;
    111     for(int i=0;i<=e[m];i++)
    112         dfs(m+1,(ll)s*pw(p[m],i));
    113 }
    114 int main()
    115 {
    116 //    freopen("in.txt","r",stdin);
    117 //    freopen("out.txt","w",stdout);
    118     init();
    119     while(scanf("%llu",&n)!=EOF){
    120 //        cout<<n<<endl;
    121         fac(n);
    122         cn=0;
    123         dfs(0,1);
    124         sort(an,an+cn);
    125         printf("%d",cn);
    126         for(int i=0;i<cn;i++)
    127             printf(" (%llu,%llu)",an[i].a,an[i].b);
    128         printf("
    ");
    129     }
    130     return 0;
    131 }
    View Code
  • 相关阅读:
    Hexo yilia 主题启用及相关设置
    Hexo Next 主题启用及相关设置
    值得一用的 Windows 软件清单
    ES6新特性2
    ES6新特性1
    手写promise第三天
    手写promise第一天
    Generator异步函数
    函子Functor
    柯里化函数组合的学习
  • 原文地址:https://www.cnblogs.com/xin-hua/p/3411301.html
Copyright © 2011-2022 走看看