uva10780 质因子分解

UVA - 10780

Again Prime? No Time.(uva卡得一逼,所以还是把vj的链接贴一下把)

题意:给出n,m,使得m^k是n!的因子,求最大的k

思路:质因子分解,将m 和n!都分解为 p1^a1*p2^a2*...pn^an,其中p1 p2...pn是连续的质数2,3,5,7...,用一个数组记录每个质数的次幂ai,然后二分答案k,只有当m分解的质因子的次幂*k全部小于等于n!分解的质因子次幂,m^k才是n!的因子,比较坑的一点是,当k=0时是作为无解的情况的

AC代码:

#include "iostream"
#include "string.h"
#include "stack"
#include "queue"
#include "string"
#include "vector"
#include "set"
#include "map"
#include "algorithm"
#include "stdio.h"
#include "math.h"
#pragma comment(linker, "/STACK:102400000,102400000")
#define ll long long
#define endl ("
")
#define bug(x) cout<<x<<" "<<"UUUUU"<<endl;
#define mem(a,x) memset(a,x,sizeof(a))
#define mp(x,y) make_pair(x,y)
#define pb(x) push_back(x)
#define ft (frist)
#define sd (second)
#define lrt (rt<<1)
#define rrt (rt<<1|1)
using namespace std;
const long long INF = 1e18+1LL;
const int inf = 1e9+1e8;
const int N=1e5+100;
const ll mod=1e9+7;

int n,m,num;
ll p[N],p1[N],p2[N];
bool ispri[N];
int init_prime(){
    int c=0, n=10005;
    mem(ispri,true);
    ispri[1]=0;
    for(ll i=2; i<=n; ++i){
        if(ispri[i]){
            p[++c]=i;
            for(ll j=i*i; j<=n; j+=i){
                ispri[j]=0;
            }
        }
    }
    return c;
}

bool check(int k){
    for(int i=1; i<=num; ++i){
        if(p1[i]<p2[i]*k) return 0;
    }
    return 1;
}

int main(){
    ios::sync_with_stdio(false),cin.tie(0),cout.tie(0);
    int T=10,t=0;
    num=init_prime();
    cin>>T;
    while(T--){
        mem(p1,0), mem(p2,0);
         //m=2,n=5;
        cin>>m>>n;
        int nu[N];
        for(int i=1; i<=n; ++i) nu[i]=i;

        for(int i=1; i<=num && p[i]<=n; ++i){
            for(int j=p[i]; j<=n; j+=p[i]){
                int d=0;
                while(nu[j]%p[i]==0){
                    d++;
                    nu[j]/=p[i];//bug("x")
                }
                p1[i]+=d;

            }
        }
        for(int i=1; i<=num && p[i]<=m; ++i){
            int d=0;
            while(m%p[i]==0){
                d++;
                m/=p[i];
            }
            p2[i]+=d;
        }
        int l=1, r=1e9, ans=0;
        while(l<=r){
            int mid=l+r>>1;
            if(check(mid)){
                ans=mid;
                l=mid+1;
            }
            else r=mid-1;
        }
        cout<<"Case "<<++t<<":"<<endl;
        if(ans) cout<<ans<<endl;
        else cout<<"Impossible to divide
";
    }
    return 0;
}
原文地址:https://www.cnblogs.com/max88888888/p/7284395.html