形成N的非素数对是2个不同的非素数,其中数的乘积是N.
1·; = N&LT = 10 ^ 6
例如对于N = 24,有2个好对(非素对形成N)(4,6),(1,24),但是(2,12),( 3,8)不好。
注意:任何2个数字a和b对(a,b)=对(b,a)。
还有另一个条件,即如果数字是一个特殊数字,那么output = -1否则计算非素数的数量。
如果数字可以表示为三个素数的乘积,则称为特殊数字。示例:12是一个特殊数字,因为12 = 2 * 2 * 3;
我尝试使用 https://en.wikipedia.org/wiki/Sieve_of_Eratosthenes 进行暴力破解, 取O(N * log(log(N))。
“除了暴力之外,还有其他更优化的解决方法吗?”
任何想法都将受到赞赏。
提前致谢。
答案 0 :(得分:1)
首先,Eratosthenes'筛子是O(N * log(log(N))列出所有下面的素数或等于N (当well implemented时)。
第二:假设你在Q
素数中考虑了你的数字,其中多重性在没有筛选的情况下是O(sqrt(N))最差的过程(最差:你的数字是素数)。所以你有一张地图:
至少有2个素因子乘以多少除数?
嗯,它们会有 m0*m1*...mq
[在此更正]。为什么?那么,准备一个列出所有除数的列表,每个因子的权力(包括p i 0 == 1),但是除掉那些幂{ {1}}。
1
种m0
除法p0 p0
除数的方法
m1
种生成除{p} p1
除数的除数的方法
mQ
具有非素数除数的所有组合的数量(因为pQ
已包含在每个集合中,并且每个素数因子本身被排除)将是所有上述子集的笛卡尔积的基数 - 因此因此,个人基数的乘积1
代码 - Java
m0*m1*...mq
答案 1 :(得分:1)
由于你没有提到约束,我假设1< = N< = 10 ^ 6 实施筛子并同时存储数量最大的素数因子10 ^ 6。
这里的代码是相同的。
int a[1000001];
a[1]=1;
for(int i=2;i*i<1000001;i++)
{
if(a[i]==0)
{
for(int j=2*i;j<1000001;j+=i)
a[j]=i;
}
}
现在如果数字是素数,你的答案是0。
if(a[n]==0)
cout<<'0';
如果是半素数(两个素数的乘积),你的答案将是1。
if(a[n/a[n]]==0)
cout<<"1";
如果它很特别,那么
int x=n/a[n];
if(a[x/a[x]]==0)
cout<<"-1";
如果它不满足上述任何条件,则计算所有非素数除数。
int c=0;
for(int i=1;i*i<n;i++)
{
if(n%i==0)
{
if(a[i]!=0&&a[n/i]!=0)
c++;
}
}
希望这有帮助!