什么是流?
流是一种将整体数据分割成多个小块依次进行处理的方式。
举个形象的例子:
山上有1000颗拳头大的小石子,需要搬下山。
- 传统的处理方式:安排一辆大卡车,一次性将石子全部运下山。
- 流的处理方式:修建一条管道,将小石子一颗颗的丢进管道,自己滚下山。
流的类型
共四种:
- Readable -可读流【数据源】-- 可读
- Writable -可写流-- 可写
- Duplex -双向流-- 可读+可写
- Transform -转换流【数据加工厂】-- 操作被写入数据,然后读出结果。
流的事件和方法
常用事件有:
- 可读流读取数据时触发 data 事件
// chunk 为数据片段 readableSrc.on("data", (chunk) => {});
- 可读流读取数据完成时触发 end 事件
// chunk 为数据片段 readableSrc.on("end", (chunk) => {});
- 可写流写完数据时触发 finish 事件
可读流的常用方法有:
- 用管道传输 pipe()
- 关闭管道传输 unpipe()
- 读取数据 read ()
- 将数据推回内部缓冲区 unshift()
- 继续读取数据 resume()
- 暂停传输 pause()
- 判断是否暂停传输 isPaused()
- 指定编码类型 setEncoding()
可写流的常用方法有:
- 写入 write()
- 结束写入 end()
- 将数据写入内存 cork()
- 取消写入内存 uncork()
- 指定默认编码类型 setDefaultEncoding()
Node.js 内支持流的内置模块
流的使用
读取文件输出到控制台
import { createReadStream } from "fs"; // 创建可读流 const readableSrc = createReadStream("./test.txt"); // 将可读流的内容输出到控制台 readableSrc.pipe(process.stdout);
读取文件并输出到新文件
import { createReadStream, createWriteStream } from "fs"; // 创建可读流 const readableSrc = createReadStream("./test.txt"); // 创建可写流 const writeSrc = createWriteStream("./test2.txt"); // 将可读流的内容通过管道传输到可写流中 readableSrc.pipe(writeSrc); // 若不存在test2.txt,则会创建test2.txt,内容与test.txt相同 // 若已存在test2.txt,则会清空test2.txt的原内容,并将test.txt的内容写入其中,最终test2.txt的内容与test.txt相同
最后的 pipe 相当于
// chunk 为数据片段 readableSrc.on("data", (chunk) => { writeSrc.write(chunk); }); readableSrc.on("end", () => { writeSrc.end(); });
读取文件并压缩打包
import { createReadStream, createWriteStream } from "fs"; // 导入方法--创建.gz的压缩包 import { createGzip } from "zlib"; // 创建可读流 const readableSrc = createReadStream("./test.txt"); // 创建可写流 const writeSrc = createWriteStream("./test.gz"); // 先将可读流的内容通过管道传输到转换流进行压缩打包 // 再将转换流中的压缩包数据通过管道传输到可写流中 readableSrc.pipe(createGzip()).pipe(writeSrc);
此处的 createGzip() 是一个转换流