C 这段代码的大O是什么?

C 这段代码的大O是什么?,c,time-complexity,big-o,C,Time Complexity,Big O,最近我参加了一个考试,其中有一个问题:g的时间复杂度是多少 int f(int *arr, int n, int m) { if(n == 0) { if(m == 0) return 3; return arr[m] + f(arr, n, m - 1); } return f(arr, n - 1, m); } int g(int *arr, int n) { return f(arr, n

最近我参加了一个考试,其中有一个问题:g的时间复杂度是多少

int f(int *arr, int n, int m)
{
    if(n == 0)
    {
        if(m == 0)
            return 3;

        return arr[m] + f(arr, n, m - 1);
    }

    return f(arr, n - 1, m);
}

int g(int *arr, int n)
{
    return f(arr, n, n);
}
现在,我和我的大多数朋友都回答了O(n),因为很明显,有2*n个函数需要f,而没有其他函数,但是教授的答案是O(n^2)。 有人能给我解释一下谁是对的吗?如果是他,你能解释一下原因吗

在帖子中,我意识到我解决了错误的问题。当内部函数调用是
f(arr,m,m-1)
时,我正在求解。在这种情况下,时间复杂度实际上是O(n²)。问题的发布方式,时间复杂度为O(n)。然而,我将离开这篇文章,因为这很可能是教授误解它的方式。因此,下面的答案很可能是以供参考的方式写的

考虑已采取的步骤:

  • 递归调用
    f()
    n次,这意味着
    n==0
    n调用堆栈
  • 现在,在这个最低的函数调用中,我们可以输入if语句
  • 我们再次调用
    f()
    ,减少了m,但通过使用m作为第二个参数来调用来保持原始的n值
  • 在这个“新”递归堆栈中,我们必须首先再次调用
    f()
    n(或m)次,然后才能再次将m减少1
  • 一旦
    m==0
    ,我们就可以返回
  • 看看这个图,其中每个“单元”代表一个对
    f()
    的调用。当
    n==0
    时,我们再次使用第三个参数调用,并将m减少1,因此我们降低了一个级别。


    由于此图中矩形的面积为
    n*m
    m==n
    ,这意味着
    f()
    被称为
    次,代码的时间复杂度为O(n²)。

    如所述为O(n),您的分析是正确的。您确定没有错误地转录问题,内部调用是到
    f(arr,m,m-1)
    ?如前所述,在内部调用
    f(arr,n,m-1)
    中引用
    n
    没有多大意义,因为在这一点上
    n
    始终是0。我非常仔细地检查了它,它是n而不是m。我怀疑教授实际上把它错当成了m,并因此说了O(n^2)。
    O(n*m)
    但是函数调用是
    n==m
    ,所以它的
    O(n^2)
    “我们再次调用f(),减少了m,但保持了原来的n值”-这是怎么回事?打电话时n始终为0。抱歉,现在正在编辑问题。看来我解决错问题了。不过,这可能是它的初衷。因此,编辑将重点关注这一点。