1053: [HAOI2007]反素数ant

1053: [HAOI2007]反素数ant

Time Limit: 10 Sec   Memory Limit: 162 MB
Submit: 2581   Solved: 1454
[ Submit][ Status][ Discuss]

Description

  对于任何正整数x,其约数的个数记作g(x)。例如g(1)=1、g(6)=4。如果某个正整数x满足:g(x)>g(i) 0<i<x
,则称x为反质数。例如,整数1,2,4,6等都是反质数。现在给定一个数N,你能求出不超过N的最大的反质数么

Input

  一个数N(1<=N<=2,000,000,000)。

Output

  不超过N的最大的反质数。

Sample Input

1000

Sample Output

840

HINT

Source

[ Submit][ Status][ Discuss]




爆搜爆搜爆搜

如果知道一个数的质因数组成,就能知道它的因数个数

设x分解质因数后,不同的质数分别是a1,a2,a3,...an

它们的个数分别是b1,b2,b3,...bn

那么x的因数个数为∏(bi+1)

显然,答案需要的是[1,n]内因数最多且它本身大小最小的数

这样的数分解质因数后它的质因数都不会很大

我们随便拿前30个质数,每个质数预处理30次方

这样就能搜索了



一开始没注意本身大小最小这一条件


#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
using namespace std;

typedef long long LL;
LL INF = 2000000000;

LL a2,mi[51][31],pri[1000];
int a1,n,tot;
bool p[100000];

void dfs(int x,LL p,LL q)
{
	if (x == 31) return;
	if (p*(1LL<<(31-x)) < a2) return;
	if (p > a2) a1 = q,a2 = p;
	if (p == a2 && q < a1) a1 = q;
	for (int j = 1; j <= 30; j++) {
		if (mi[x][j] == 0) break;
		if (q*mi[x][j] > n) break;
		dfs(x+1,p*1LL*(j+1),q*mi[x][j]);
	}
	dfs(x+1,p,q);
}

int main()
{
	#ifdef YZY
		freopen("yzy.txt","r",stdin);
	#endif
	
	cin >> n;
	for (int i = 2; i < 100000; i++) 
		if (!p[i]){
			int j = i*2;
			while (j < 100000) 
				{p[j] = 1; j += i;}
		}
	for (int i = 2; i < 1000; i++)
		if (!p[i]) pri[++tot] = i;
	for (int i = 1; i <= 50; i++) {
		mi[i][0] = 1;
		for (int j = 1; j <= 30; j++) {
			mi[i][j] = mi[i][j-1]*pri[i];
			if (mi[i][j] >= INF) break;
		}
	}
	dfs(1,1,1);
	cout << a1;
	return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值