CF912E Prime Gift 數學
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
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
Print a single line featuring the k-th smallest integer. It‘s guaranteed that the answer doesn‘t exceed 1018.
Examples Input Copy3Output Copy
2 3 5
7
8Input Copy
5Output Copy
3 7 11 13 31
17
93
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.
首先在1e18的範圍內,那麽質數的個數最多只有16個,你可以將這16個列出來然後相乘,看看多大;
那麽我們分開算;
不妨將奇數位置的dfs和偶數位置的分別dfs;
分別算出包含這些因子的所有可能值,如果對數組開多大不確定,用 vector.push_back就好;
那麽我們要求第k大,考慮二分答案;
那麽對於我們之前求出的那兩個集合,我們用 two-pointer 來掃一遍確定當前答案是第幾個;
然後調整上下界即可;
#include<iostream> #include<cstdio> #include<algorithm> #include<cstdlib> #include<cstring> #include<string> #include<cmath> #include<map> #include<set> #include<vector> #include<queue> #include<bitset> #include<ctime> #include<deque> #include<stack> #include<functional> #include<sstream> //#include<cctype> //#pragma GCC optimize(2) using namespace std; #define maxn 300005 #define inf 0x3f3f3f3f //#define INF 1e18 #define rdint(x) scanf("%d",&x) #define rdllt(x) scanf("%lld",&x) #define rdult(x) scanf("%lu",&x) #define rdlf(x) scanf("%lf",&x) #define rdstr(x) scanf("%s",x) typedef long long ll; typedef unsigned long long ull; typedef unsigned int U; #define ms(x) memset((x),0,sizeof(x)) const long long int mod = 1e9 + 7; #define Mod 1000000000 #define sq(x) (x)*(x) #define eps 1e-3 typedef pair<int, int> pii; #define pi acos(-1.0) const int N = 1005; #define REP(i,n) for(int i=0;i<(n);i++) typedef pair<int, int> pii; inline ll rd() { ll x = 0; char c = getchar(); bool f = false; while (!isdigit(c)) { if (c == ‘-‘) f = true; c = getchar(); } while (isdigit(c)) { x = (x << 1) + (x << 3) + (c ^ 48); c = getchar(); } return f ? -x : x; } ll gcd(ll a, ll b) { return b == 0 ? a : gcd(b, a%b); } ll sqr(ll x) { return x * x; } /*ll ans; ll exgcd(ll a, ll b, ll &x, ll &y) { if (!b) { x = 1; y = 0; return a; } ans = exgcd(b, a%b, x, y); ll t = x; x = y; y = t - a / b * y; return ans; } */ int n; int p[30]; ll k; vector<ll>vc[2]; int tmp[30]; int cnt; void dfs(int belong, ll val, int cur) { vc[belong].push_back(val); for (int i = cur; i <= cnt; i++) { if (1e18 / tmp[i] >= val) { dfs(belong, val*tmp[i], i); } } } ll sol(ll x) { ll res = 0; int j = 0; for (int i = vc[0].size() - 1; i >= 0; i--) { while (j < vc[1].size() && vc[1][j] <= x / vc[0][i])j++;// 雙指針掃一遍 res += j; } return res; } int main() { //ios::sync_with_stdio(0); rdint(n); for (int i = 1; i <= n; i++)rdint(p[i]); rdllt(k); for (int i = 1; i <= n; i++)if (i & 1)tmp[++cnt] = p[i]; dfs(0, 1, 1); cnt = 0; for (int i = 1; i <= n; i++)if (i % 2 == 0)tmp[++cnt] = p[i]; dfs(1, 1, 1); sort(vc[0].begin(), vc[0].end()); sort(vc[1].begin(), vc[1].end()); ll l = 1, r = 1e18; while (l <= r) { ll mid = (l + r) / 2; if (sol(mid) >= k)r = mid - 1; else l = mid + 1; } cout << l << endl; return 0; }
CF912E Prime Gift 數學