2011-12-30 60 views
6

我遍歷包含文件名的數組。對於他們每個人,我調用readFile()。當調用相應的回調函數時,我希望檢索傳遞給readFile()的文件名作爲參數。可以做到嗎?NodeJS readFile()檢索文件名

封閉了一段剪切代碼,以更好地解釋我的意圖。

var fs = require("fs"); 
var files = ["first.txt", "second.txt"]; 
for (var index in files) { 
    fs.readFile(files[index], function(err, data) { 
     //var filename = files[index]; 
     // If I am not mistaken, readFile() is asynchronous. Hence, when its 
     // callback is invoked, files[index] may correspond to a different file. 
     // (the index had a progression). 
    }); 

} 
+0

請檢查以下所有解決方案。每個都是正確的。 – MrIzik 2011-12-30 17:54:31

回答

6

你也可以使用forEach代替for循環:

files.forEach(function (file){ 
    fs.readFile(file, function (err, data){ 
    console.log("Reading %s...", file) 
    }) 
}) 
+0

這是最簡單,最可讀,最正確的答案! – TooTallNate 2011-12-30 17:45:43

+0

這是正確的,但如果需要預處理則會有一些限制。 – MrIzik 2011-12-30 17:51:23

7

你可以做,使用封閉:

for (var index in files) { 
    (function (filename) { 
     fs.readFile(filename, function(err, data) { 
      // You can use 'filename' here as well. 
      console.log(filename); 
     }); 
    }(files[index])); 
} 

現在每個文件名保存爲一個函數的參數,也不會被環路繼續其迭代的影響。

0

您也可以使用Function.prototype.bind預先設定參數。 bind將返回一個新的函數,該函數在調用時以files [index]作爲第一個參數調用原始函數。

但不知道這是否是一個好辦法。

var fs = require("fs"); 
var files = {"first.txt", "second.txt"}; 
for (var index in files) { 
    fs.readFile(files[index], 
     (function(filename, err, data) { 
      //filename 
     }).bind(null, files[index]) 
    ); 

} 
+0

在這種情況下,'Function#bind()是完全不必要的,只是性能上的損失。在這種情況下,您只需要爲每個循環迭代創建一個新的閉包。使用'Array#forEach()',就像@danmactough所暗示的,在我看來是「最乾淨」的方式。 – TooTallNate 2011-12-30 17:45:22

+0

感謝您打開我的眼睛 – MrIzik 2011-12-30 17:53:54