hihoCoder #1692 : 第K小分数

描述

给定N个不同的质数P1, P2, ... PN。用它们作为分目可以组成(P1-1) + (P2-1) + ... (PN-1)个分数:

1/P1, 2/P1, 3/P1, ..., P1-1/P1, 1/P2, 2/P2, 3/P2, ... P2-1/P2, ... 1/PN, 2/PN, ... PN-1/PN  

请帮助小Ho求出其中第K小的分数。

输入

第一行包含两个整数N和L。  

以下N行每行包含一个质数Pi。  

对于70%的数据,1 ≤ N ≤ 100, 1 ≤ K ≤ 1000000, 2 ≤ Pi ≤ 100000  

对于100%的数据, 1 ≤ N ≤ 1000, 1 ≤ K ≤ 1000000000, 2 ≤ Pi ≤ 1000000000

输出

输出一个分数表示答案

样例输入

3 4  
2  
3  
5

样例输出

1/2

二分答案

扫描二维码关注公众号,回复: 5975163 查看本文章
#include<cstdio>
using namespace std;
int p[1005], son, prt;
int n, k;
int findnum(double x)
{
    long long cnt = 0, tmp;
    for(int i = 1; i <= n; i++){
        tmp = x * p[i];
        cnt += tmp;
        if(cnt > k) return 1;
        if(son == -1){
            son = tmp;
            prt = p[i];
        }
        else if((long long)son*p[i] < (long long)prt*tmp){
            son = tmp;
            prt = p[i];
        }
    }
    if(cnt < k) return -1;
    return 0;
}
int main()
{
    while(scanf("%d%d",&n,&k) == 2){
        for(int i = 1; i <= n; i++){
            scanf("%d",&p[i]);
        }
        double l = 0, r = 1, mid;
        int tmp;
        while(1){
            son = -1; prt = -1;
            mid = (l+r)/2;
            tmp = findnum(mid);
            if(tmp == 1) r = mid;
            else if(tmp == -1) l = mid;
            else{
                printf("%d/%d\n",son,prt);
                break;
            }
        }
    }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/kkjy_00/article/details/88130153