容斥定理 hdu2204 Eddy's爱好

传送门:点击打开链接

很明显会有大量重复的被计算,所以很容易就想到容斥定理。

我们设dp[i]表示能表示成M^i(i>1)且i是这个数字能表示出来的最大的情况时的总类数

比如,27拆成M^K时的K最大能表示成3,所以27这个数字分在dp[3]这一类

1我们暂时不考虑,不把它放在任何一类

因为K>1,所以K至少是2,最大是2^K=N的时候,所以K最大等于log2(N),所以K非常的小

首先,求出K最大大概的位置

然后开始求dp[i]。求法如下:

首先,1~N中有哪些是能拆分成M^i的,利用pow函数可以算出来,暂时记为dp[i]

按照dp[i]的要求,还必须要排除K目前不是表示最大的情况,相当于容斥了,如下

dp[i]=dp[i]-dp[2*i]-dp[3*i]-dp[4*i]-.......

这样处理完后,dp[i]就是能表示成M^i(i>1)且i是这个数字能表示出来的最大的情况时的总类数了

最后的答案就是dp[2]+dp[3]+....+dp[K的最大值],再加上我们之前没考虑的1就可以了

#include<map>
#include<set>
#include<cmath>
#include<stack>
#include<queue>
#include<cctype>
#include<cstdio>
#include<string>
#include<vector>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<functional>
#define FIN freopen("input.txt","r",stdin)
#define FOUT freopen("output.txt","w+",stdout)

using namespace std;
typedef long long LL;
typedef pair<int, int> PII;

const int MX = 1e3 + 5;
const double exps = 1e-8;

LL dp[MX];

int main() {
    LL n;//FIN;
    while(~scanf("%I64d", &n)) {
        memset(dp, 0, sizeof(dp));
        int p = ceil(log2(1.0 * n)) + 1;

        LL ans = 1;
        for(int i = p; i >= 2; i--) {
            dp[i] = pow(1.0 * n, 1.0 / i) - 1 + exps;
            for(int j = 2 * i; j <= p; j += i) {
                dp[i] -= dp[j];
            }
            ans += dp[i];
        }
        printf("%I64d\n", ans);
    }
    return 0;
}

版权声明:本文为博主原创文章,未经博主允许不得转载。

容斥定理 hdu2204 Eddy's爱好

时间: 2024-10-12 20:33:47

容斥定理 hdu2204 Eddy's爱好的相关文章

HDU2204 Eddy&#39;s爱好(容斥原理)

题目问[1,n]有几个数是$m^k (k>1)$形式. 如果这样考虑,m已知k未知,对于每一个m统计其k的数量即$\lfloor log_mn \rfloor$个,再容斥,然而m太多了,完全不可行. 而k远远比m还少,应该反过来考虑,m未知k已知,对于每一个k统计其m的数量,即$\lfloor \sqrt[k]n \rfloor$个. 由于$n \leqslant 10^{18}$,而$2^{60} > 10^{18}$,所以k的范围就是小于60的整数. 然而60用容斥$2^{60}$还是不可

HDU2204 Eddy&#39;s爱好

题意:问[1,n]有几个是m^k的形式(m>0,k>1, n<=1e18) 题解:枚举m,会发现很多,所以枚举k,可以发现k<=63那么只要每个k计算pow(n , 1/k),接下来去重,可以用容斥来做,2^61的复杂度,这里考虑m^k = m^(k1+k2)一个合数可以分解为素数,那么只要对素数容斥就可以了 #include <bits/stdc++.h> #define maxn 101000 #define INF 0x3f3f3f3f typedef long

HDU 1796 How many integers can you find (容斥定理 + 二进制)

How many integers can you find Time Limit: 12000/5000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 5493    Accepted Submission(s): 1567 Problem Description Now you get a number N, and a M-integers set, you should

hdu2204 Eddy&#39;s爱好 打表+容斥原理

Ignatius 喜欢收集蝴蝶标本和邮票,但是Eddy的爱好很特别,他对数字比较感兴趣,他曾经一度沉迷于素数,而现在他对于一些新的特殊数比较有兴趣.这些特殊数是这样的:这些数都能表示成M^K,M和K是正整数且K>1.正当他再度沉迷的时候,他发现不知道什么时候才能知道这样的数字的数量,因此他又求助于你这位聪明的程序员,请你帮他用程序解决这个问题.为了简化,问题是这样的:给你一个正整数N,确定在1到N之间有多少个可以表示成M^K(K>1)的数. 打表+容斥原理 1 #include<stdi

cf451E Devu and Flowers 卢卡斯定理+容斥定理

题目:http://codeforces.com/problemset/problem/451/E 题意:有n个盒子(n<=20),每个盒子中有10^12个小球,现从每个盒子中取出若干球(可为0),求共取出s个小球(s<=10^14)的方案数. 组合数学问题,求C(n,m).但n,m过大时,可用卢卡斯定理. 卢卡斯定理:C(n,m) %p = C(n/p,m/p) * C(n%p,m%p) 从n个盒子中取出s个球的方案数,相当于插板,即 C(s+n-1,n-1).注意这是没有限制条件的情况.

HDU1796 How many integers can you find【容斥定理】

题目链接: http://acm.hdu.edu.cn/showproblem.php? pid=1796 题目大意: 给你一个整数N.和M个整数的集合{A1.A2.-.Am}.集合内元素为非负数(包括零),求小于N的 正整数(1~N-1)中,能被M个整数的集合中随意一个元素整除的正整数个数. 比如N = 12.M = {2,3},在1~N-1中,能被2整除的数为{2,4,6.8.10},能被3整除的数为 {3.6,9}.则所求集合为{2,3,4.6,8,9,10},共7个,则答案为7. 思路:

HDU 1695 GCD(容斥定理)

GCD Time Limit: 6000/3000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 7529    Accepted Submission(s): 2773 Problem Description Given 5 integers: a, b, c, d, k, you're to find x in a...b, y in c...d that GCD(x, y

GCD SUM 强大的数论,容斥定理

GCD SUM Time Limit: 8000/4000MS (Java/Others) Memory Limit: 128000/64000KB (Java/Others) SubmitStatus Problem Description 给出N,M执行如下程序:long long  ans = 0,ansx = 0,ansy = 0;for(int i = 1; i <= N; i ++)   for(int j = 1; j <= M; j ++)       if(gcd(i,j)

HDU5768Lucky7(中国剩余定理+容斥定理)(区间个数统计)

When ?? was born, seven crows flew in and stopped beside him. In its childhood, ?? had been unfortunately fall into the sea. While it was dying, seven dolphins arched its body and sent it back to the shore. It is said that ?? used to surrounded by 7