2016-11-17 69 views
0

我遇到了意外的行爲,涉及fs.createReadStreamfs.createWriteStream。我希望有人能指出,我做出了錯誤的假設:可讀可寫的流意外行爲

我創建這樣

let readableStream = fs.createReadStream('./lorem ipsum.doc'); 
let writableStream = fs.createWriteStream('./output'); 

可讀和可寫流爲什麼,如果我讀流發送到寫入流這樣

let data, chunk; 
readableStream 
.on('readable',() => { 
    while ((chunk=stream.read()) !== null) { 
     data+=chunk; 
    } 
}) 
.on('end',()=>{ 
    writableStream.write(data) 
    console.log("done"); 
}); 

我結束了在輸出文件差異

Output file with discrepancy

而如果I流是這樣的:

let data, chunk; 
readableStream 
.on('readable',() => { 
    while ((chunk=stream.read()) !== null) { 
     writableStream.write(chunk) 
    } 
}) 
.on('end',()=>{ 
    console.log("done"); 
}); 

所有細而如預期:

Expected output

即,在第一例中,何時/何是以字節爲單位的額外開銷添加?爲什麼添加?出了什麼問題?

感謝您的啓發!


注:我知道使用pipe(這給了我正確的輸出文件),但這些例子只是我的理解。

回答

1

我猜測的重點是在第一個演示中,您使用'data + =',它將二進制流轉換爲字符串,並浪費了一些空間。你可以嘗試轉換第二個演示嗎? ===>

var s=chunk; 
writableStream.write(s); 

更新:結合流緩衝區正確的方法是像您的評論:

var chunks = []; 
var size = 0; 
...on('data', function(chunk){ 
    chunks.push(chunk); 
    size += chunk.length; 
}) 
...on('end', function(){ 
    var buf = Buffer.concat(chunks, size); // use buf to write to writestream 
    var str = iconv.decode(buf, 'utf8'); // use str to console.log string, which supports all languages such as Asian 
}) 
+0

是的,你說得對。如果我做'let data = Buffer.from([]);',然後使用'data = Buffer.concat([data,chunk]);',文件就出來了。我愚蠢的,我沒有意識到我正在轉換爲字符串類型。 –

+0

或者實際上,這個JavaScript轉換爲字符串類型... :) –