44 # 流的原理

简介: 44 # 流的原理

通过 fs 模块实现拷贝功能

同步的拷贝实现

新建 name.txt 文件,里面添加

凯小默的博客

const fs = require("fs");
const path = require("path");
// 读取默认不指定编码都是 buffer 类型
let r = fs.readFileSync(path.resolve(__dirname, "./name.txt"));
console.log(r);
// 默认会将二进制转化成字符串到文件,虽然看到的是字符串但是内部存储的是二进制
fs.writeFileSync(path.resolve(__dirname, "./new_name.txt"), r);

执行上面同步代码

异步的拷贝实现,不会阻塞主线程,node 是底层是 libuv,内部工作原理是多线程

const fs = require("fs");
const path = require("path");
fs.readFile(path.resolve(__dirname, "./name.txt"), function (err, data) {
    if (err) throw err;
    fs.writeFile(path.resolve(__dirname, "./new_name2.txt"), data, function (err) {
        if (err) throw err;
        console.log("写入成功");
    });
});

直接使用 copyFile,它的原理就是读写操作

const fs = require("fs");
const path = require("path");
fs.copyFile(path.resolve(__dirname, "./name.txt"), path.resolve(__dirname, "./new_name3.txt"), function (err) {
    if (err) throw err;
    console.log("name.txt was copied to new_name3.txt");
});

stream

拷贝文件会默认把整个文件读取一遍,特点不能读取比内存大的文件(会占用很多可用的内存),这个时候可以使用 stream 流,边读边写(采用分块读取写入的方式来实现拷贝),流的原理就是读一点写一点。

文件系统中内置了操作文件的方法(精确的读取文件中的部分内容)

I/O 操作:读取就是写入内存,写入就是把内存取,读取出来

读取操作:

新建 read.txt,添加 0123456789 内容

const fs = require("fs");
const path = require("path");
// 先读取三个到内存中
const buf = Buffer.alloc(3);
// 打开文件读取文件
// open(path, flags, callback)
// flags:r(读取),w(写入),a(追加文件)
fs.open(path.resolve(__dirname, "./read.txt"), "r", function (err, fd) {
    // fd: Number 表示的是文件描述器(file descriptor)
    // read(fd, buffer, offset, length, position, callback: (err, bytesRead, buffer)
    // buffer 的第 0 个位置开始写入,写入到 buffer 中几个,文件的读取位置是多少
    fs.read(fd, buf, 0, 3, 0, function (err, bytesRead, buffer) {
        // bytesRead: 真正的读取个数
        if (err) throw err;
        console.log("读取成功", bytesRead, buffer);
    });
});

写操作:

const fs = require("fs");
const path = require("path");
const wBuf = Buffer.from("凯小默");
// open(path, flags, mode, callback)
// w(写入)默认会先清空在写入,a(追加文件)
// mode:表示权限,这个可以看【拓展 Linux ls 命令】部分,默认就是 666 的权限,0o666 就是 438
fs.open(path.resolve(__dirname, "./write.txt"), "a", 438, function (err, fd) {
    if (err) throw err;
    // write(fd, buffer, offset, length, position, callback: (err, written, buffer)
    // 0 代表就是从 buffer 0 的位置开始读取,读取 6 个写入到文件的哪个位置中
    fs.write(fd, wBuf, 0, 9, 0, function (err, written, buffer) {
        if (err) throw err;
        console.log("写入成功", written, buffer);
    });
});

w 改成 a,再次执行

拓展 Linux ls 命令

Linux ls 命令

  • -a:显示所有文件及目录 (. 开头的隐藏文件也会列出)
  • -d:只列出目录(不递归列出目录内的文件)。
  • -l:以长格式显示文件和目录信息,包括权限、所有者、大小、创建时间等。
  • -r:倒序显示文件和目录。
  • -t:将按照修改时间排序,最新的文件在最前面。
  • -A:同 -a ,但不列出 "." (目前目录) 及 ".." (父目录)
  • -F:在列出的文件名称后加一符号;例如可执行档则加 "*", 目录则加 "/"
  • -R:递归显示目录中的所有文件和子目录。

在使用 ls -l 命令时,第一列的字符表示文件或目录的类型和权限。其中第一个字符表示文件类型,例如:

  • -:表示普通文件
  • d:表示目录
  • l:表示符号链接
  • c:表示字符设备文件
  • b:表示块设备文件
  • s:表示套接字文件
  • p:表示管道文件

在使用 ls -l 命令时,第一列的其余 9 个字符表示文件或目录的访问权限,分别对应三个字符一组的 rwx 权限。例如:

  • r:表示读取权限
  • w:表示写入权限
  • x:表示执行权限
  • -:表示没有对应权限

前三个字符表示所有者的权限,中间三个字符表示所属组的权限,后三个字符表示其他用户的权限。例如:

输入下面命令

ls -al

假设有下面这一行:

-rw-r--r-- 1 guok 197609   18 Jun 28 10:00 name.txt

表示文件名为 name.txt 的文件,所有者具有读写权限,所属组和其他用户只有读取权限。

最常见的更改文件权限命令:

chmod 777 name.txt

这里的 777 三位数字分别代表 user、group、other 的权限(都为7)。

  • 若要 rwx 属性则 4 + 2 + 1 = 7
  • 若要 rw- 属性则 4 + 2 = 6
  • 若要 r-x 属性则 4 + 1 = 5
目录
相关文章
|
1月前
|
消息中间件 存储 数据库
RocketMQ 流存储解析:面向流场景的关键特性与典型案例
RocketMQ 流存储解析:面向流场景的关键特性与典型案例
88363 0
|
5月前
|
存储 C语言 C++
66 C++ - 流的概念和流类库的结构
66 C++ - 流的概念和流类库的结构
37 0
|
6月前
|
Java
java流是指在Java中用来读写数据的一组有序的数据序列,它可以将数据从一个地方带到另一个地方。java流分为输入流和输出流,输入流是从源读取数据的流,而输出流是将数据写入到目的地的流。Java流又可以分为字节流和字符流,字节流读取的最小单位是一个字节(1byte=8bit),而字符流一次可以读取一个字符(1char = 2byte = 16bit)。Java流还可以分为节点流和处理流,节点流是直接从一个源读写数据的流(这个流没有经过包装和修饰),处理流是在对节点流封装的基础上的一种流。
104 0
|
7月前
I/O流
IO流:I的全称是Input,O的全称是Output。表示读取,流可以看做是程序传输数据的通道。 作用:解决程序请求资源,输出资源的问题。
34 0
|
8月前
|
SQL JavaScript 前端开发
开始使用流
Java 8 中的 Stream 俗称为流,它与 java.io 包里的 InputStream 和 OutputStream 是完全不同的概念 Stream 用于对集合对象进行各种非常便利、高效的聚合操作,或者大批量数据操作 Stream API 借助于 Lambda 表达式,极大的提高编程效率和程序可读性 同时它提供串行和并行两种模式进行汇聚操作,并发模式能够充分利用多核处理器的优势 通过下面的例子我们可以初步体会到使用 Stream 处理集合的便利性
31 1
|
8月前
其他流
其他流
34 0
|
9月前
|
存储 Java
流及其相关操作
流及其相关操作
|
9月前
|
Java 数据库
I/O 流总结
I/O 流总结
62 0
|
9月前
|
存储 Java
探索Stream流的实际应用场景
在Java 8中,引入了Stream流这一强大的新特性,它不仅可以让我们更加优雅地处理集合数据,还可以提高代码的简洁性和性能。本文将深入探讨Stream流的实际应用场景,从而帮助读者更好地理解和应用这一功能。
374 0
|
10月前
|
存储 Java
【Java I/O 流】I/O 流的原理与流的分类
所谓 I/O 是 Input/Output 的缩写,即输入/输出。I/O 技术用于处理数据的传输,文件的读写等。 数据传输可以看做是一种数据的流动,而流(Stream)可以理解为数据传输时的序列。按照数据的“流向”,流可分为输入流和输出流。
64 1