我知道最近访问的文件会被缓存到 RAM 中,但是是否有用于频繁执行的命令的缓存?
例如,如果我运行cat file.txt
多次,file.txt
则会在第一个命令后缓存。
- 但是如果我运行
ps aux
多次,第一个命令的输出会被缓存在某处吗? - 每个应用程序是否都有自己的常用命令缓存;例如
git log
?
阅读完这个相关问题后,我认为正确的术语是memoization。
我知道最近访问的文件会被缓存到 RAM 中,但是是否有用于频繁执行的命令的缓存?
例如,如果我运行cat file.txt
多次,file.txt
则会在第一个命令后缓存。
ps aux
多次,第一个命令的输出会被缓存在某处吗?git log
?阅读完这个相关问题后,我认为正确的术语是memoization。
系统将缓存与命令可执行文件关联的文件以及命令运行时从磁盘读取的任何文件。后续命令执行可能会受益于该缓存,并且需要更少或不需要物理磁盘读取操作。这对用户和命令本身都是透明的。
但是输出不会被缓存。每次执行命令都会生成新的输出,即使该输出与上次运行命令时的输出相同。
在
ps aux
示例中,ps
调查当前进程列表并根据给定的参数输出该列表。系统无法输出输出的缓存变体(因为没有这样的缓存)以避免运行ps
。同样,git log
将访问并输出当前存储库的日志。系统无法避免执行命令,也无法避免让其读取存储库的存储状态等。命令可能会受益于文件系统缓存、缓冲区等缓存的各种数据,但输出每次都会从头开始重新生成。
实现命令输出的通用缓存将非常棘手,因为您通常不知道对系统的哪些更改会使缓存失效。有些命令要求文件更改后才能生成不同的输出,而其他命令会由于时间流逝、随机机会或其他事件的发生而生成不同的输出。除了输出到标准输出之外,命令还可能具有许多副作用,例如以各种方式更新文件数据,这使得缓存输出更加困难且通常毫无意义(因为将输出发送到标准输出流可能不是运行命令的主要原因)。
单个命令可能会缓存其输出或使用检查点来避免重新进行昂贵的中间计算。不过,它们会在特定问题领域内执行此操作(各种编译器缓存、科学软件中确定性模拟的检查点等),而操作系统不会为它们透明地执行此操作。特别是,操作系统无法避免执行这些命令而只是输出结果。
操作系统缓存磁盘块和 inode,但实际上不缓存文件。磁盘块缓存会产生明显的文件缓存副作用。
应用程序没有操作系统级缓存。一些执行高开销操作的应用程序可能有自己的缓存,这些缓存是应用程序通过将文件写入磁盘来实现的。
例如,如果您查看主目录,可能会有一个名为的隐藏目录
~/.cache/
,其中包含应用程序缓存文件。同样,也可能存在全局缓存/var/cache/
。但是,像 ps 这样的命令实际上并不需要缓存,因为它的输出非常动态,而且生成成本并不高,因此缓存的意义不大。相比之下,它
atop
依赖于进程记账来收集长期进程信息;它可以在 10 秒内收集这些信息,也可以从进程记账缓存中提取这些信息。在 Linux 中,虽然操作系统采用缓存机制来提高性能(例如将文件内容缓存在 RAM 中以加快后续访问),但它不会缓存命令的标准输出 (stdout)。
Linux 不会缓存命令的标准输出。每次执行命令都会根据当前系统状态生成新输出。虽然操作系统会缓存文件内容以优化访问,并且某些应用程序会实施自己的缓存策略,但命令的标准输出仍未缓存,以确保准确性和相关性。