首页 > 其他分享 >POJ 2773 Happy 2006 二分+容斥原理(二进制枚举或dfs)

POJ 2773 Happy 2006 二分+容斥原理(二进制枚举或dfs)

时间:2023-04-03 20:07:46浏览次数:55  
标签:ll 2773 容斥 mid dfs 互素 factor include sum


Happy 2006

Time Limit: 3000MS Memory Limit: 65536KTotal Submissions: 14003 Accepted: 4946

Description

Two positive integers are said to be relatively prime to each other if the Great Common Divisor (GCD) is 1. For instance, 1, 3, 5, 7, 9...are all relatively prime to 2006. 

Now your job is easy: for the given integer m, find the K-th element which is relatively prime to m when these elements are sorted in ascending order. 

Input

The input contains multiple test cases. For each test case, it contains two integers m (1 <= m <= 1000000), K (1 <= K <= 100000000).

Output

Output the K-th element in a single line.

Sample Input


2006 1


2006 2


2006 3


Sample Output


1


3


5


Source

POJ Monthly--2006.03.26,static

算法分析:

题意:

给你m和k,求第k个与m互质的数。

分析:

另一种做法,虽然没这个快,但好理解(点这里)

 

 

根据唯一分解定理: 对一个数进行因式分解, 最终必定能分解为多个素数相乘的式子, 且这个式子是唯一的(1除外)。

我们假设1~mid就是满足有k个与m互素的数,然后我们保证mid最小就可以了。

二分的思想,从k到inf进行二分,二分出最小的mid(mid有可能存在12个与m互素的数,但mid与m不互素)符合有k个与m互素的数的数。

对于就1到mid中有多少个与m互素的数需要用到容斥原理:

比如假设m=12;mid=13

12=2*2*3

那么1到mid中与m不互质的数就有2,3,4,6,8,9,10,12,

其实就是2的所有倍数,以及3的所有倍数

这样我们就 算出与1到13中与12不互素的个数为: 13/2+13/3-13/(2*3)=8;

容斥原理:详细解释

POJ 2773 Happy 2006  二分+容斥原理(二进制枚举或dfs)_i++

第二个公式/

互素的数就位13-8=5;

所以与m不互素的数其实对m进行因式分解,容斥原理。

代码实现:

#include<cstdio>  
#include<cstring>  
#include<cstdlib>  
#include<cctype>  
#include<cmath>  
#include<iostream>  
#include<sstream>  
#include<iterator>  
#include<algorithm>  
#include<string>  
#include<vector>  
#include<set>  
#include<map>  
#include<stack>  
#include<deque>  
#include<queue>  
#include<list> 
using namespace std;
typedef long long ll;
const int maxn = 1e6+10;
const ll LNF = 9e18;
ll fac[maxn]; 
ll m,k,sum=0;
void init()           //获取质因子
{
    sum = 0;
    ll tmp = m;
    for(ll i = 2; i*i<=tmp; i++)    //官方版的唯一分解定理
    if(tmp%i==0)
    {
        fac[sum++] = i;
        while(tmp%i==0) tmp /=  i;
    }
    if(tmp>1) fac[sum++] = tmp;
}
ll cal(ll temp)
{
	if(m==1) return temp;
	if(temp==1) return 1;//两个剪枝
	
	ll ret=0;
	//二进制枚举
	 for(int i = 1; i < (1<<sum); i++) //从0~2^n-1个状态,遍历每一个集合
    {
    	
    	ll cnt=0,p=1;
        for(int j = 0; j <sum; j++) //遍历二进制的每一位
        {
            if(i & (1 << j))//判断二进制第j位是否存在
            {
            	p*=fac[j];
                cnt++;
            }
        }
        if(cnt&1)      //cnt为奇数   ,容斥原理
		{
			ret+=temp/p;
		}
		else
		{
			ret-=temp/p;
		}
    }
    
    return temp-ret;

}
int two()
{
	
	ll l=k,r=LNF,mid;
	while(l<=r)
	{
		mid=(l+r)/2;
		if(cal(mid)>=k)
		{
			r=mid-1;
		}
		else
		{
			l=mid+1;
		}
	}
	printf("%lld\n",l);    
}
int main()
{
     while(scanf("%lld%lld",&m,&k)!=EOF)
	 {
	 	 init();
	 	 two();
	 }
    return 0;
}

dfs

ll n, k;
ll factor[MAXN], sz;
ll sum, mid;
 
void prime_factor(ll n) {
    sz = 0;
    for (ll i = 2; i*i <= n; i++) if (n%i == 0) {
        factor[sz++] = i;
        while (n%i == 0) n /= i;
    }
    if (n > 1) factor[sz++] = n;
}
 
void dfs(ll id, ll step, ll num) {
    if (id == sz) {
        if (step != 0) {
            if (step & 1) sum += mid / num;
            else sum -= mid / num;
        }
        return;
    }
    dfs(id + 1, step, num);
    if (num*factor[id] <= mid)
        dfs(id + 1, step + 1, num*factor[id]);
}
 
int main() {
    while (cin >> n >> k) {
        prime_factor(n);
        ll l = k, r = 1e18, ans = l;
        while (l <= r) {
            mid = (l + r) / 2;
            sum = 0;
            dfs(0, 0, 1);
            if (mid - sum >= k) r = mid - 1, ans = mid;
            else l = mid + 1;
        }
        cout << ans << endl;
    }
    return 0;
}

 

标签:ll,2773,容斥,mid,dfs,互素,factor,include,sum
From: https://blog.51cto.com/u_14932227/6167159

相关文章

  • 【FastDFS分布式文件系统】5.FastDFS客户端的配置、启动和常用命令
    上一篇我们介绍了FastDFS服务端的tracker追踪服务器和storage存储服务器,本篇来介绍一下客户端的启动,以及外部客户端如何与FastDFS服务端进行连接。和之前一样,服务端部署在三台服务器上:其中192.168.195.129是tracker追踪服务器,192.168.195.130和192.168.195.131......
  • 【FastDFS分布式文件系统】6.FastDFS客户端启动与Java连接
    上一篇我们讲解了如何配置和启动FastDFS客户端,以及客户端上传下载的一些常用命令。那么,在许多需要进行分布式文件上传与下载的系统中,就不能像执行Linux命令一样去上传和下载文件,它们需要使用开发系统的语言去操作客户端使用其命令与服务端进行交互,此时FastDFS......
  • dfs理解
    dfs理解201深搜(DFS)哔哩哔哩bilibili董晓-博客园(cnblogs.com)深搜的时机在扩展当前节点的邻边之前,即for当前节点的儿子节点之前,刚进入当前这个节点。for完当前节点的所有儿子节点之后,要离开当前节点了。开始for当前节点的扩展邻边时,即刚从当前节点出去。此时可以从父节点向......
  • AcWing 第 97 场周赛 ABC(dfs)
    https://www.acwing.com/activity/content/competition/problem_list/3088/果然绩点成绩和竞赛水平总得寄一个(tome4944.热身计算#include<bits/stdc++.h>usingnamespacestd;typedeflonglongLL;typedefpair<LL,LL>PII;constLLMAXN=1e18,MINN=-MAXN,INF=0x3f3f3......
  • 【算法专题】容斥原理
    【算法专题】容斥原理题E.DevuandFlowershttps://codeforces.com/contest/451/problem/E前置知识:隔板法然后正难则反,把至多取\(a_i\)个转化为至少取\(a_i+1\)的反问题,就能套用隔板法的公式了。答案即为:#include<bits/stdc++.h>#definelllonglongusingname......
  • hdfs disk balancer 磁盘均衡器
    目录1、背景2、hdfsbalancer和hdfsdiskbalancer有何不同?3、操作3.1生成计划3.2执行计划3.3查询计划3.4取消计划4、和diskbalancer相关的配置5、额外知识点5.1新的block存储到那个磁盘(卷)中5.2磁盘数据密度度量标准6、参考文档1、背景在我们的hadoop集群运行一段过......
  • HDFS Balancer负载均衡器
    目录1、背景2、什么是平衡2.1每个DataNode的利用率计算2.2集群的利用率2.3平衡3、hdfsbalancer语法4、运行一个简单的balance案例4.1设置平衡数据传输带宽4.2执行ban......
  • FastDFS并发问题的排查经历
    附件用的fastdf上传和下载的,本地开发时就没考虑过多文件上传就会有并发的问题,比如多个只上传成功了一个或者上传了但是文档内容缺失了,变成0字节。呵。。都是一次难忘的经......
  • MongoDB GridFS最佳应用概述
    《MongoDBGridFS最佳应用概述》作者:chszs,转载需注明。GridFS是MongoDB数据库之上的一个简单文件系统抽象。如果你熟悉AmazonS3的话,那么GridFS与之相似。为什么像MongoDB这......
  • 容斥与反演技巧(二)
    年更大作FJOI2017矩阵填数\(\max=v\)拆成\(\lev\)和存在一个\(=v\),对第二个条件容斥发现变成\(<v\),离散化后对每个点求出上界直接算。复杂度\(O(n^32^n)\)。......