• 牛客练习赛14 A-n的约数


    链接:https://www.nowcoder.com/acm/contest/82/A
    来源:牛客网

    时间限制:C/C++ 1秒,其他语言2秒
    空间限制:C/C++ 262144K,其他语言524288K
    64bit IO Format: %lld

    题目描述

    t次询问,每次给你一个数n,求在[1,n]内约数个数最多的数的约数个数

    输入描述:

    第一行一个正整数t
    之后t行,每行一个正整数n

    输出描述:

    输出t行,每行一个整数,表示答案
    示例1

    输入

    5
    13
    9
    1
    13
    16

    输出

    6
    4
    1
    6
    6

    备注:

    对于100%的数据,t <= 500 , 1 <= n <= 1000000000000000000

    分析:设ans为n以内约数个数最多的数,
    根据唯一分解定理,ans=p1^e1*p2^e2*......pk^ek,pi为素数且p1<p2<...<pk,
    那么必有e1>=e2>=...>=ek,(贪心)即后一个素数的幂肯定小于等于前一个素数的幂,
    根据这点用dfs搜索。
    #include<cstdio>
    long long N;
    long long cnt,ans;//ans为1到N约数个数最多的数,cnt为它的约数个数 
    long long p[15]={2,3,5,7,11,13,17,19,23,29,31,37,41,43,47}; 
    /*设ans=p1^e1*p2^e2*......pk^ek,pi为素数且p1<p2<...<pk 
    那么必有e1>=e2>=...>=ek 
    */ 
    void dfs(int k,long long sum,long long num,int lim)//k表示当前素数的下标 
    {//num表示数sum的合数个数, lim表示素因子最多为lim个(lim<=15) 
        if(k>14) return;
        if(num>cnt) cnt=num,ans=sum;
        if(num==cnt&&ans>sum) ans=sum;
        for(int i=1;i<=lim;i++)//即后一个素数的幂肯定小于等于前一个素数的幂
            if(sum<=N/p[k]) 
            {sum*=p[k];dfs(k+1,sum,num*(i+1),i);}
    }
    int main()
    {
        int T;
        scanf("%d",&T);
        while(T--)
        {
            scanf("%lld",&N);
            ans=cnt=1;
            dfs(0,1,1,15);
            printf("%lld
    ",cnt);
        }
        return 0;
    }
    View Code












  • 相关阅读:
    nodepad++中的正则表达式匹配和替换操作。
    QT Creator配置环境和安装
    圣诞树小程序的制作
    C#编辑xml文件
    delegate里的Invoke和BeginInvoke
    记录RFID操作错误
    关于Panel隐藏横向滚动条
    随笔
    Java图形打印 上下对称三角星
    Centos 7.5安装 Redis 5.0.0
  • 原文地址:https://www.cnblogs.com/ACRykl/p/8682002.html
Copyright © 2020-2023  润新知