2016-07-05 69 views
2

我很難理解爲什麼我在JavaScript中編寫的遞歸函數有問題。當我給它一個大的json文件時,它會陷入無限循環。我有一種感覺,它與JavaScript關閉如何工作有關。跳一些聰明的人可以看看我的代碼並解釋發生了什麼。JavaScript遞歸古怪行爲?

我已經將行的函數行移植到PHP,它產生了我期望的輸出。

的JavaScript:

var jsonfile = process.argv[2]; 

json = require("./"+jsonfile); 

path = "2"; 

buildPaths(json, path); 

function buildPaths(json, path) { 

    if (json.Children == null || json.Children.length == 0) { 

     console.log(path + "/" + json.TypedItemId); 

    } else { 

     for (i = 0; i < json.Children.length; i++) { 
      buildPaths(json.Children[i], path + "/" + json.TypedItemId); 
     } 
    } 

} 

移植到PHP:用於測試

<?php 
$jsonfile = $argv[1]; 
$json = json_decode(file_get_contents($jsonfile)); 

$path = "2"; 

buildPaths($json, $path); 

function buildPaths($json, $path) { 


    if ($json->Children == null || count($json->Children) == 0) { 

     echo $path . "/" . $json->TypedItemId . "\n"; 

    } else { 

     for ($i = 0; $i < count($json->Children); $i++) { 
      buildPaths($json->Children[$i], $path . "/" . $json->TypedItemId); 
     } 
    } 

} 

樣品JSON文件(文件較大造成更大的怪事):

{ 
    "TypedItemId": 4, 
    "Children": [ 
    { 
     "TypedItemId": 67, 
     "Children": [ 
     { 
      "TypedItemId": 90, 
      "Children": [ 
      { 
       "TypedItemId": 90, 
       "Children": [ 
       { 
        "TypedItemId": 67, 
        "Children": [ 
        { 
         "TypedItemId": 90, 
         "Children": [ 
         { 
          "TypedItemId": 90, 
          "Children": [] 
         }, 
         { 
          "TypedItemId": 908, 
          "Children": [] 
         } 
         ] 
        }, 
        { 
         "TypedItemId": 908, 
         "Children": [ 
         { 
          "TypedItemId": 90, 
          "Children": [] 
         }, 
         { 
          "TypedItemId": 908, 
          "Children": [] 
         } 
         ] 
        } 
        ] 
       } 
       ] 
      }, 
      { 
       "TypedItemId": 908, 
       "Children": [] 
      } 
      ] 
     }, 
     { 
      "TypedItemId": 908, 
      "Children": [ 
      { 
       "TypedItemId": 90, 
       "Children": [] 
      }, 
      { 
       "TypedItemId": 908, 
       "Children": [] 
      } 
      ] 
     } 
     ] 
    } 
    ] 
} 

PHP輸出(正確):

2/4/67/90/90/67/90/90 
2/4/67/90/90/67/90/908 
2/4/67/90/90/67/908/90 
2/4/67/90/90/67/908/908 
2/4/67/90/908 
2/4/67/908/90 
2/4/67/908/908 

JavaScript的節點輸出(不正確):

2/4/67/90/90/67/90/90 
2/4/67/90/90/67/90/908 
+0

你沒有在你的JS代碼的任何封鎖。只是一個正常的功能。 –

+0

好吧 仍然對引起不同產出的事情感到好奇。我想知道是什麼關於JavaScript,我不明白,導致我看到 –

回答

4

沒有錯,你的JavaScript,除了迭代器使用的是在你的循環:

for (i = 0; i < json.Children.length; i++) { 

相反的聲明使用var一個局部變量您在全局對象上使用屬性i作爲迭代器,它將在所有調用buildPaths之間共享。

使用本地變量,而不是:

for (var i = 0; i < json.Children.length; i++) { 

自己嘗試一下:

var json = {"TypedItemId":4,"Children":[{"TypedItemId":67,"Children":[{"TypedItemId":90,"Children":[{"TypedItemId":90,"Children":[{"TypedItemId":67,"Children":[{"TypedItemId":90,"Children":[{"TypedItemId":90,"Children":[]},{"TypedItemId":908,"Children":[]}]},{"TypedItemId":908,"Children":[{"TypedItemId":90,"Children":[]},{"TypedItemId":908,"Children":[]}]}]}]},{"TypedItemId":908,"Children":[]}]},{"TypedItemId":908,"Children":[{"TypedItemId":90,"Children":[]},{"TypedItemId":908,"Children":[]}]}]}]}; 
 

 
var path = "2"; 
 

 
buildPaths(json, path); 
 

 
function buildPaths(json, path) { 
 
    if (json.Children == null || json.Children.length == 0) { 
 
     console.log(path + "/" + json.TypedItemId); 
 
    } else { 
 
     for (var i = 0; i < json.Children.length; i++) { 
 
      buildPaths(json.Children[i], path + "/" + json.TypedItemId); 
 
     } 
 
    } 
 
}

+0

輝煌的結果!我是一個全球變量LOL。現在測試它。 Ty =) –

+1

爲了方便捕捉這些類型的錯誤,請確保使用'strict strict'啓用嚴格模式。 –

+0

是的!感謝您成爲我的代碼審查的目光。 –