Java 这个简单程序的运行时间-时间复杂性
我试图弄清楚这个简单程序的时间复杂度是多少,但我似乎不明白什么是最好的方法 我已经为每一行并排写下了时间复杂度Java 这个简单程序的运行时间-时间复杂性,java,algorithm,time,time-complexity,big-o,Java,Algorithm,Time,Time Complexity,Big O,我试图弄清楚这个简单程序的时间复杂度是多少,但我似乎不明白什么是最好的方法 我已经为每一行并排写下了时间复杂度 1 public int fnA (int n) { 2 int sum = 0; O(1) 3 for (int i = 0; i < n; i++) { O(n) 4 int j = i; O(n) 5 i
1 public int fnA (int n) {
2 int sum = 0; O(1)
3 for (int i = 0; i < n; i++) { O(n)
4 int j = i; O(n)
5 int product = 1; O(1)
6
7 while (j > 1) { O(n)
8 product ∗= j; O(log n)
9 j = j / 2; O(log n)
10 }
11 sum += product; O(1)
12 }
13 return sum; O(1)
14 }
否对于每个i,都有
logn
循环运行,因此对于n
元素,总复杂度为nlogn
因为您知道下面的循环使用logn
while (j > 1) {
product ∗= j;
j = j / 2;
}
现在,对每个
i
执行此特定循环。这将执行n次。因此它变成了nlogn
算法的时间复杂度是O(nlogn)
for
循环执行N次(从0
到N
)
while
循环执行了logN
次,因为您每次都将数字除以一半
由于您在for
的内部执行,因此您正在执行logN
操作N次,从那里开始执行O(NlogN)
所有剩余的运算(赋值、乘法、除法、求和)您可以假设需要O(1)
以上程序的关键是while循环,它是定义因子,其余行的复杂度不会超过O(n),并假设算术运算将在O(1)时间内运行
上面的循环的运行时间为O(log(j)),而j的变化范围为1到n,因此它的系列
-> O(log(1) + log(2) + log(3) + log(4).....log(n))
-> O(log(1*2*3*4...*n))
-> O(log(n!))
and O(log(n!)) is equal to O(n log(n))
有关上述证明,请首先参考,您可以计算所有操作。例如:
1 public int fnA (int n) {
2 int sum = 0; 1
3 for (int i = 0; i < n; i++) {
4 int j = i; n
5 int product = 1; n
6
7 while (j > 1) {
8 product ∗= j; ?
9 j = j / 2; ?
10 }
11 sum += product; n
12 }
13 return sum; 1
14 }
1公共整数fnA(整数n){
2整数和=0;1
3表示(int i=0;i1){
8产品∗= J
9 j=j/2?
10 }
11总和+=乘积;n
12 }
13返回金额;1
14 }
现在我们可以做计数了:它的总数是:2+3n+nlog(n)
在许多程序中,计数更为复杂,通常有一个突出的高阶项,例如:2+3n+2n2。当谈到性能时,我们真正关心的是n大的时候,因为当n小的时候,总和还是小的。当n较大时,高阶项会拖拽其余项,因此在本例中,2n2才是真正重要的项。这就是tilde近似的概念
考虑到这一点,通常可以快速确定执行频率最高的代码部分,并使用其计数来表示总体时间复杂度。在OP给出的示例中,它如下所示:
for (int i = 0; i < n; i++) {
for (int j = i; j > 1; j /= 2)
product *= j;
}
for(int i=0;i1;j/=2)
乘积*=j;
}
给∑log2n。通常计数涉及离散数学,我学到的一个技巧是用积分代替它并计算:∫ log2n=nlog(n)你能详细说明你是如何得到这个答案的吗?@RandomMath:更新了答案。while循环while(j>1)不是O(n)?@RandomMath:它只是循环中的一个操作,实际上是O(1)。虽然它运行了n次,所以你可以把它看作O(n)。整个循环是while(j>1){积∗= j、 j=j/2;}正如您在问题中提到的,这完全需要logn时间。从技术上讲,甚至是产品∗= J为O(1)操作,j=j/2;这也是O(1)操作。但是,由于这些操作在特定的i。。。所以它变成了一个特定i的logn。当i从0循环到n时,因此这个logn循环被执行n次,使其nlogn。
1 public int fnA (int n) {
2 int sum = 0; 1
3 for (int i = 0; i < n; i++) {
4 int j = i; n
5 int product = 1; n
6
7 while (j > 1) {
8 product ∗= j; ?
9 j = j / 2; ?
10 }
11 sum += product; n
12 }
13 return sum; 1
14 }
for (int i = 0; i < n; i++) {
for (int j = i; j > 1; j /= 2)
product *= j;
}