我试图确定以下函数的Big O表示法
public static int f10(int n)
{
return f1(n*n*n)
}
其中f1()由:
给出public static int f1(int n)
{
int sum = 0;
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++)
sum++;
for (int j = 0; j < n; j++)
sum++;
for (int j = 0; j < n; j++)
sum++;
}
return sum;
}
我可以看到O(f1)是O(n ^ 2),但是当我们调用f10时,这会变成O(n ^ 6),因为在调用f1之前n的大小是立方的吗?
我理解f1的复杂性并没有从它自己的角度改变,但它是从f10的角度来看的?&#39; n&#39;
答案 0 :(得分:2)
让我们分析f1()
:
for (int i = 0; i < n; i++) -> O(n)
for (int j = 0; j < n; j++)
for (int j = 0; j < n; j++)
for (int j = 0; j < n; j++) -> O(n)
for (n-times) { O(n) } -> O(n^2)
所以f1()
是O(n ^ 2)。它只是两个嵌套循环。但是因为使用n ^ 3调用f1()
,所以使f10()
确实为O(n ^ 6)。
然而,上述复杂性顺序是理论上的。实际上,它可能取决于您如何调用f10()
和/或编译器所做的优化。智能C编译器可以用简单的O(1)算术表达式替换f1()
。
然后,将f1()
简化为表达式,编译器可以用结果替换f10(42)
之类的调用,在编译时进行所有计算。
f1()
到一个简单的O(1)表达式?
答案 1 :(得分:2)
O(n^2)
的复杂性总是f10
,这很清楚。但是,O(n^6)
的复杂性确实是f1
,因为它依赖于使用参数n^3
调用的f1
。为简单起见,假设f10
是内联函数。 public static int f10(int n)
{
int sum = 0;
for (int i = 0; i < n^3; i++) {
for (int j = 0; j < n^3; j++)
sum++;
for (int j = 0; j < n^3; j++)
sum++;
for (int j = 0; j < n^3; j++)
sum++;
}
return sum;
}
的正文看起来像这样:
n^3
现在很容易推断 - 两级嵌套循环,每一级都有O(n^6)
次迭代 - &gt; f10
。如果您仍然不相信,请尝试查看n = 1 -> 3 iterations
n = 2 -> 8 * 3 * 8 = 3 * 2^6 iterations
n = 3 -> 27 * 3 * 27 = 3 * 3^6 iterations
....
n = k -> k^3 * 3 * k^3 = 3 * k^6 iterations
的运行时间如何随着输入的增加而增加:
{{1}}