[HDU6623]Minimal Power of Prime

壹、题目描述 ¶

传送门 to HDU.

贰、题解 ¶

真·妙妙题。

考虑将次数可能大于 \(4\) 的质数全部筛出来暴力查,并把它们从 \(n\) 中除掉,那么剩下的因数中,只有可能是以下几种情况:

\[\begin{matrix} a^4 &a^3 &a^2(\text{include }x^2y^2\text{ and others}) &a &a^3b &a^2b &\cdots \end{matrix} \]

只有刚好是某数的 \(4,3,2\) 次方时比较特殊,其他情况下都是 \(1\) 了。

时间复杂度降到 \(\mathcal O(Tn^{1\over 5})\).

叁、参考代码 ¶

#include<cstdio>
#include<cmath>
#include<algorithm>
using namespace std;

#define NDEBUG
#include<cassert>

namespace Elaina{
    #define rep(i, l, r) for(int i=(l), i##_end_=(r); i<=i##_end_; ++i)
    #define drep(i, l, r) for(int i=(l), i##_end_=(r); i>=i##_end_; --i)
    #define fi first
    #define se second
    #define mp(a, b) make_pair(a, b)
    #define Endl putchar('\n')
    #define mmset(a, b) memset(a, b, sizeof a)
    // #define int long long
    typedef long long ll;
    typedef unsigned long long ull;
    typedef pair<int, int> pii;
    typedef pair<ll, ll> pll;
    template<class T>inline T fab(T x){ return x<0? -x: x; }
    template<class T>inline void getmin(T& x, const T rhs){ x=min(x, rhs); }
    template<class T>inline void getmax(T& x, const T rhs){ x=max(x, rhs); }
    template<class T>inline T readin(T x){
        x=0; int f=0; char c;
        while((c=getchar())<'0' || '9'<c) if(c=='-') f=1;
        for(x=(c^48); '0'<=(c=getchar()) && c<='9'; x=(x<<1)+(x<<3)+(c^48));
        return f? -x: x;
    }
    template<class T>inline void writc(T x, char s='\n'){
        static int fwri_sta[1005], fwri_ed=0;
        if(x<0) putchar('-'), x=-x;
        do fwri_sta[++fwri_ed]=x%10, x/=10; while(x);
        while(putchar(fwri_sta[fwri_ed--]^48), fwri_ed);
        putchar(s);
    }
}
using namespace Elaina;

const int maxn=1e4;

int prime[maxn+5], pcnt;
bool vis[maxn+5];
inline void sieve(){
    vis[1]=1;
    for(int i=2; i<=maxn; ++i){
        if(!vis[i]) prime[++pcnt]=i;
        for(int j=1; j<=pcnt && i*prime[j]<=maxn; ++j){
            vis[i*prime[j]]=1;
            if(i%prime[j]==0) break;
        }
    }
}

ll n;

signed main(){
    sieve(); // writc(pcnt);
    int T=readin(1);
    while(T--){
        n=readin(1ll);
        int ans=100;
        for(int i=1; i<=pcnt && 1ll*prime[i]*prime[i]<=n; ++i) if(n%prime[i]==0){
            int cnt=0;
            while(n%prime[i]==0) n/=prime[i], ++cnt;
            ans=min(ans, cnt);
        }
        if(n!=1){
            ll r;
            r=round(pow(n, 1.0/4));
            if(r*r*r*r==n) ans=min(ans, 4);
            else{
                r=round(pow(n, 1.0/3));
                if(r*r*r==n) ans=min(ans, 3);
                else{
                    r=round(pow(n*1.0, 0.5));
                    if(r*r==n) ans=min(ans, 2);
                    else if(n!=1) ans=1;
                }
            }
        }
        writc(ans);
    }
    return 0;
}

肆、关键之处 ¶

把特殊的因子特殊处理,其他情况讨论一下。

posted @ 2021-07-23 22:25  Arextre  阅读(50)  评论(0编辑  收藏  举报