如何解决Codility CommonPrimeDivisors 时间复杂度?
关于 Codility 中的 Common Prime Divisors 任务,我有几个时间复杂度问题。问题如下:
素数是一个正整数X,它恰好有两个不同的 除数:1 和 X。前几个素数是 2、3、5、7、11 和 13.
素数 D 被称为正整数 P 的素数除数,如果有 存在一个正整数 K 使得 D * K = P。例如,2 和 5 是 20 的质数。
给定两个正整数 N 和 M。目标是检查 整数 N 和 M 的素因数集是否恰好是 一样。
例如,给定:
- N = 15 和 M = 75,质因数相同:{3,5};
- N = 10 和 M = 30,质因数不一样:{2,5} 不等于 {2,3,5};
- N = 9 和 M = 5,素数除数不一样:{3} 不一样 等于 {5}。
class Solution { public int solution(int[] A,int[] B); }
即,给定两个非空数组 A 和 B 的 Z 个整数,返回 A[K] 和 B[K] 的素数除数所对应的位置数 K 完全一样。
例如,给定:
A[0] = 15 B[0] = 75
A[1] = 10 B[1] = 30
A[2] = 3 B[2] = 5
该函数应该返回 1,因为只有一对 (15,75) 具有相同的素数除数集。
为以下假设编写一个有效的算法:
- Z 是 [1..6,000] 范围内的整数;数组 A 的每个元素,
- B 是 [1..2,147,483,647] 范围内的整数。
class Solution {
public int solution(int A[],int B[]) {
int result = 0;
for (int i = 0; i < A.length; i++){
int gcdOfAAndB = gcd(A[i],B[i]);
if (
factorsOfRemainderAreTheSameOfGCD(A[i],gcdOfAAndB) &&
factorsOfRemainderAreTheSameOfGCD(B[i],gcdOfAAndB)
) {
result++;
}
}
return result;
}
public boolean factorsOfRemainderAreTheSameOfGCD(int input,int gcdOfAAndB) {
int factorsnotinGCD = input / gcdOfAAndB;
while (gcdOfAAndB % factorsnotinGCD != 0){
int gcd = gcd(gcdOfAAndB,factorsnotinGCD);
if (gcd == 1)
return false;
factorsnotinGCD /= gcd;
}
return true;
}
public int gcd(int a,int b) {
if (a % b == 0){
return b;
}
return gcd(b,a % b);
}
}
我假设算法的时间复杂度为:
O(Z * (log(log(M+N)+N) * log(N) + log(log(M+N)+M) * log(M)))
,因为:
- while 循环中的 GCD 以
log(log(M+N)+input)
的方式执行; - while 循环本身显然具有对数增长率:factorsnotinGCD 在每次迭代中至少减半;
- 因此我得出结论,它们组合起来代表
log(log(M+N)+input) * log(input)
; - 由于 while 循环执行两次,一次用于 N 和 M,我们将它们相加,结果
(log(log(M+N)+N) * log(N) + log(log(M+N)+M) * log(M)
; - 最后,Z 表示将要测试的 N 和 M 的数量。
我的问题:
- 我对算法时间复杂度的假设是否正确?如果不是,正确的时间复杂度是多少?
- Codility 表示它检测到时间复杂度为
O(Z * log(max(A) + max(B))**2)
,我想知道如何实现这一点。
先谢谢了
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。