簡體   English   中英

計算遞歸調用

[英]Counting recursive calls

是否有一個數學公式來計算遞歸函數的調用次數,而無需與我的編譯器核對

當通過調用mystery2(1000)調用mystery2時,將遞歸調用多少次?

 public void mystery2(int n)
   {
  if (n <= 1)
    System.out.print(n);
  else 
  {
    mystery2(n / 2);            
    System.out.print(", " + n);
  }
}

1、3、7、15、31、62、125、250、500、1000 = 10次

使用log2(n)中的ceil

ceil(log2(1000)) = ceil(9.966) = 10

沒有“公式”,但是有一種解決遞歸的通用技術。 在這里你有復發

N(x) = 1 + N(floor(x / 2))

與基本情況

N(1) = 1

N(x)的定義是“如果mystery2的初始參數為xmystery2被調用的次數”。

重復性可以通過“技巧”來解決,這些技巧可以像積分公式一樣學習,也可以通過奇特的數學運算(如生成函數)來學習。 有時近似值是您可以做的最好的事情。 在您的情況下,如果我們取消了發言權運算符(或假設x是2的冪),那么很明顯

N(x) = 1 + log_2(x)

我們可以驗證這一點。 如果x為1,我們有N(x) = 1 + 0 = 1 對於x = 2 ,我們有N(x) = 1 + 1 = 2 ,依此類推...對於x = 1024 ,它是N(x) = 1 + 10 = 11

使用發言權算子,確切的答案要復雜得多,具體取決於x的奇數個因子,但是上面的公式始終很接近。

另一種選擇是將計數傳遞給您的方法。

public void mystery2(int n) {
  mystery2(n, 1);
}

public void mystery2(int n, int count) {
  if (n <= 1)
    System.out.print(n);
  else 
  {
    mystery2(n / 2, count+1);            
    System.out.print(", " + n + ":count=" + count);
  }
}

編輯:我想到了一種更好的方法。 您可以像這樣返回計數。

public static void mystery2(int n) {
    System.out.print("\ncount = " + mystery2(n, 1));
}

public static int mystery2(int n, int count) {
    if (n <= 1) {
        System.out.print(n);
        return count;
    }

    System.out.print(n + ", ");
    return mystery2(n / 2, count + 1);
}

使用靜態變量或全局變量

public void mystery2(int n)
{
  static count = 0;
  count++;
  system.out.print("We have called this " + count + "times before...");
  if (n <= 1)
    System.out.print(n);
  else
  {
    mystery2(n / 2);            
    System.out.print(", " + n);
  }

}

在方法之外,創建一個變量,例如mysteryCnt = 0; (必須初始化為0),然后在ELSE塊內,使用mysteryCnt ++方法將其遞增; 那可能行得通。

else{
   mystery2(n / 2);
   mysteryCnt ++;
   System.out.println(", " + n);
}

Jonny Z有一個正確的想法,但是您不能在方法內部初始化變量,否則它將永遠不會增加到1以上; 就像他做的那樣,它將設置為0,然后在每次調用該方法時增加為1。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM