博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
codeforces912E(折半搜索+双指针+二分答案)
阅读量:5008 次
发布时间:2019-06-12

本文共 2370 字,大约阅读时间需要 7 分钟。

E. Prime Gift

E. Prime Gift
time limit per test
3.5 seconds
memory limit per test
256 megabytes
input
standard input
output
standard output

Opposite to Grisha's nice behavior, Oleg, though he has an entire year at his disposal, didn't manage to learn how to solve number theory problems in the past year. That's why instead of Ded Moroz he was visited by his teammate Andrew, who solemnly presented him with a set of n distinct prime numbers alongside with a simple task: Oleg is to find the k-th smallest integer, such that all its prime divisors are in this set.

Input

The first line contains a single integer n (1 ≤ n ≤ 16).

The next line lists n distinct prime numbers p1, p2, ..., pn (2 ≤ pi ≤ 100) in ascending order.

The last line gives a single integer k (1 ≤ k). It is guaranteed that the k-th smallest integer such that all its prime divisors are in this set does not exceed 1018.

Output

Print a single line featuring the k-th smallest integer. It's guaranteed that the answer doesn't exceed 1018.

Examples
input
Copy
3 2 3 5 7
output
Copy
8
input
Copy
5 3 7 11 13 31 17
output
Copy
93
Note

The list of numbers with all prime divisors inside {2, 3, 5} begins as follows:

(1, 2, 3, 4, 5, 6, 8, ...)

The seventh number in this list (1-indexed) is eight.

/*

  给定一个大小为n的素数集合

  求出分解后只含这些质数因子的第k小整数

直接枚举判断显然不可以。 考虑折半搜索。可以把这16个数字拆成2个子集,各自生成所有大小1e18及以下的积。 但也需要使两个乘积组成的集合尽量接近。可以预先造出极限数据试一试集合里能有多少数 对于最坏情况,即如下数据162 3 5 7 11 13 17 19 23 29 31 37 41 43 47 53分为2 3 5 7 11 13 和  17 19 23 29 31 37 41 43 47 53 两个集合时这两个集合生成的1e18及以下的积的数量分别为 958460个 和 505756个,并不大 集合中数必须两两不等。最后统计答案, 两个集合生成的积各自排一下序然后二分答案,对于每个答案 u,可以O(|S|)双指针得到他是第几大。具体做法是枚举从到小枚举第一个集合的积 t1,然后计算一下第二个集合的积中有多少积和 t1 相乘小于等于 u,由于是从大到小枚举的,所以t1必然递增所以第二个集合的积中符合条件的积的数量也必然是递增的,所以只要扫一遍就行。 */#include
#define ll long long#define inf 1e18#define N 24using namespace std; vector
seg[2];int p[N],n;ll ansid; void dfs(int L,int R,ll val,int id){ seg[id].push_back(val); for(int i=L;i<=R;i++) if(inf/p[i]>=val) dfs(i,R,val*p[i],id);} ll cnt(ll num){ int j=0; ll ret=0; for(int i=seg[0].size()-1;i>=0;i--) { while(j
>1; if(cnt(mid)>=ansid) R=mid; else L=mid; } cout<
<
>ansid; solve(); return 0;}

 

转载于:https://www.cnblogs.com/L-Memory/p/9905612.html

你可能感兴趣的文章
hdu-5894 hannnnah_j’s Biological Test(组合数学)
查看>>
scss常规用法
查看>>
css定位position属性深究
查看>>
android中不同版本兼容包的区别
查看>>
Static 与 new 的问题【待解决】
查看>>
xml
查看>>
在 mvc4 WebApi 中 json 的 跨域访问
查看>>
敏捷开发文章读后感
查看>>
xposed获取context 的方法
查看>>
html5 canvas 图像处理
查看>>
He who hesitates is Lost
查看>>
php中引用&的真正理解-变量引用、函数引用、对象引用
查看>>
关于<form> autocomplete 属性
查看>>
OutOfMemory
查看>>
LeetCode:组合总数III【216】
查看>>
Thinkphp框架回顾(三)之怎么实现平常的sql操作数据库
查看>>
虚函数的效率问题
查看>>
POJ 1860 Currency Exchange(SPFA 判断有无“正”环)
查看>>
广告地址屏蔽
查看>>
收缩SqlServer数据库日记方法
查看>>