来源:牛客网
有n个格子,每个格子里有一个数,1,2,3,4...n
牛牛放出无穷只青蛙。
第一只青蛙的路线是:1->2->4->8->16->....
第二只青蛙的路线是:1->3->9->27->81->....
第三只青蛙的路线是:1->5->25->125....
第四只青蛙的路线是:1->7->49........
。。。。。。
用数学语言描述,第 只青蛙的路线是首项为1,公比为的等比数列,其中代表第个素数。
当青蛙跳到一个格子上,如果这个格子上面有一个数,青蛙就会把这个数吃掉。
牛牛想知道,所有没有被吃掉的数的lcm(最小公倍数 ,Least common multiple)是多少?
由于这个lcm可能非常大,请输出它对取模的值。
输入描述:
一个正整数
输出描述:
如果所有数都被吃掉了,请输出一个字符串"empty"
否则输出所有没有被吃掉的数的lcm,对取模
示例1
输入
复制
7
输出
复制
6
说明
数字 1 可以被所有青蛙吃掉;
数字 2 可以被第 1 只青蛙吃掉;
数字 3 可以被第 2 只青蛙吃掉;
数字 4 可以被第 1 只青蛙吃掉;
数字 5 可以被第 3 只青蛙吃掉;
数字 6 无法被吃掉;
数字 7 可以被第 4 只青蛙吃掉。
所以剩下的数字只有一个 6 ,所有数的 lcm 为 6
示例2
输入
复制
123456789
输出
复制
539747460
先根据唯一分解定理进行分解
每个能被筛去的数就2 ^ k , 3 ^ k , 5 ^ k
那么如果分解的质因数个数>=2个就不会被筛去了
然后n = p1^a1 , p2 ^ a2.....
然后m =p1^b1 , p2 ^ b2....
然后求最小公倍数 p1 ^ max(a1,b1)
其实就是求每个质因数的最高次幂那么如果不是2的话那他的最高次幂
2 * x ^ k <= n 用log 表述出来
如果是2就是 3 * 2 ^ k <= n 在表示出来最大值
#include <bits/stdc++.h>
using namespace std;
typedef long long LL;
const int N = 80000005 , mod = 1e9 + 7;
int n;
int p[N] , st[N];
LL ans = 1;
LL ksm(int a , int b)
{
LL res = 1 , t = b;
while(t)
{
if(t & 1) res = res * a % mod;
a = (LL) a * a % mod;
t >>= 1;
}
return res;
}
LL cal(int x)
{
if(x == 2) return ksm(x ,floor(log2(n / 3) ) );
return ksm(x , floor(log(n / 2) / log (x) ) );
}
void get_prime()
{
int cnt = 0;
for(int i= 2 ;i <= n / 2; i ++)
{
if(!st[i])
{
p[cnt ++] = i;
ans = ans * cal(i) % mod;
}
for(int j = 0 ;j < cnt && i * p[j] <= n / 2 ; j ++)
{
st[i * p[j]] = 1;
if(i % p[j] == 0) break;
}
}
}
int main()
{
cin >> n;
get_prime();
if(ans == 1) cout <<"empty"<<endl;
else
cout << ans;
}
牛客2021寒假训练营J题快速幂+筛质数
最新推荐文章于 2024-09-14 22:25:23 发布