zoukankan      html  css  js  c++  java
  • [cf920G][容斥原理+二分]

    G. List Of Integers
    time limit per test
    5 seconds
    memory limit per test
    256 megabytes
    input
    standard input
    output
    standard output

    Let's denote as L(x, p) an infinite sequence of integers y such that gcd(p, y) = 1 and y > x (where gcd is the greatest common divisor of two integer numbers), sorted in ascending order. The elements of L(x, p) are 1-indexed; for example, 9, 13 and 15 are the first, the second and the third elements of L(7, 22), respectively.

    You have to process t queries. Each query is denoted by three integers xp and k, and the answer to this query is k-th element of L(x, p).

    Input

    The first line contains one integer t (1 ≤ t ≤ 30000) — the number of queries to process.

    Then t lines follow. i-th line contains three integers xp and k for i-th query (1 ≤ x, p, k ≤ 106).

    Output

    Print t integers, where i-th integer is the answer to i-th query.

    Examples
    input
    Copy
    3
    7 22 1
    7 22 2
    7 22 3
    output
    Copy
    9
    13
    15
    input
    Copy
    5
    42 42 42
    43 43 43
    44 44 44
    45 45 45
    46 46 46
    output
    Copy
    187
    87
    139
    128
    141
    题意:求出与p互质并且>x的第k小数
    题解:首先求出p所有的质因子,状压枚举出质因子相乘的情况,比如000001表示只有一个最小的质因子,则在1-y中有y/prime[1]个,再通过容斥即可求出与p不互质的个数,此时二分答案y即可
     1 #include<bits/stdc++.h>
     2 using namespace std;
     3 #define debug(x) cout<<#x<<" is "<<x<<endl;
     4 typedef long long ll;
     5 ll sol(ll x,vector<ll>&f){
     6     ll res=0;
     7     int n=(int)f.size();
     8     for(int i=1;i<(1<<n);i++)
     9     {
    10         ll now=1,sgn=-1;
    11         for(int j=0;j<n;j++)
    12             if(i&(1<<j))now*=f[j],sgn*=-1;
    13         res+=sgn*(x/now);
    14     }
    15     return x-res;
    16 }
    17 int main(){
    18     int t;
    19     scanf("%d",&t);
    20     while(t--){
    21         ll x,p,k;
    22         scanf("%lld%lld%lld",&x,&p,&k);
    23         vector<ll>g;
    24         for(ll i=2;i*i<=p;i++){
    25             if(p%i==0){
    26                 g.push_back(i);
    27                 while(p%i==0){
    28                     p/=i;
    29                 }
    30             }
    31         }
    32         if(p>1)g.push_back(p);
    33         ll r=1000000000000LL;
    34         ll l=0;
    35         k+=sol(x,g);
    36         ll ans;
    37         while(l<=r){
    38             ll mid=(l+r)/2;
    39             if(sol(mid,g)>=k){
    40                 ans=mid;
    41                 r=mid-1;
    42             }
    43             else{
    44                 l=mid+1;
    45             }
    46         }
    47         printf("%lld
    ",ans);
    48     }
    49     return 0;
    50 }
    View Code
  • 相关阅读:
    hdu 1754 线段树 注意线段树节点的设计 求什么,设什么
    hdu 4015 概率题
    poj 1950 回溯
    最大上升子序列
    JVM学习博客
    2012
    i am alone at a crossroads
    易知难
    牢骚。。
    something
  • 原文地址:https://www.cnblogs.com/MekakuCityActor/p/10926041.html
Copyright © 2011-2022 走看看