这是我复习《UNIX系统》这门课程时记录的一些笔记 ,希望能对你有所帮助😊
i 节点
理解 i 节点能帮助你更深入掌握 Linux 文件系统的工作原理!
在 Linux/Unix 文件系统中,i 节点(inode) 是文件系统的核心数据结构,它存储了文件的元数据(metadata),但==不包含文件名或文件内容本身==
1. i 节点的基本概念
(1)文件的组成
每个文件在文件系统中由 3 部分组成:
- 文件名(File Name):用户可见的名称(如
file1
)。 - i 节点(inode):存储文件的元数据(权限、所有者、时间戳、数据块位置等)。
- 文件内容(Data Blocks):实际存储文件数据的磁盘块。
(2)查看文件的 i 节点
使用 ls -il
可以查看文件的 i 节点编号:
1 2
| $ ls -il 1234567 -rw-r--r-- 1 user group 1024 Jan 1 10:00 file1
|
1234567
是 file1
的 i 节点编号。- 其他信息(权限、所有者、大小、时间等)均存储在 i 节点中。
2. i 节点中存储的信息
每个 i 节点包含以下关键信息(通过 stat
命令可查看):
1 2 3 4 5 6 7 8
| $ stat file1 File: file1 Size: 1024 Blocks: 8 IO Block: 4096 regular file Device: 801h/2049d Inode: 1234567 Links: 1 Access: 2024-01-01 10:00:00.000000000 +0800 Modify: 2024-01-01 10:00:00.000000000 +0800 Change: 2024-01-01 10:00:00.000000000 +0800 Birth: -
|
字段 | 说明 |
---|
Inode 编号 | 文件的唯一标识(如 1234567 )。 |
文件类型 | 普通文件、目录、符号链接等。 |
权限(Mode) | 如 -rw-r--r-- (对应数字 644 )。 |
所有者(UID) | 文件属主的用户 ID。 |
所属组(GID) | 文件属组的组 ID。 |
硬链接数(Links) | 指向该 i 节点的文件名数量(见下文)。 |
文件大小 | 字节数(如 1024 )。 |
时间戳 | 访问时间(atime )、修改时间(mtime )、状态变更时间(ctime )。 |
数据块位置 | 文件内容存储在磁盘的哪些块中。 |
3. 硬链接(Hard Link)与 i 节点的关系
(1)创建硬链接
- 本质:
file1
和 file2
指向同一个 i 节点(如 1234567
)。 - 效果:
- i 节点的 硬链接计数(Links) 从
1
变为 2
。 - 修改
file1
或 file2
会同步更改文件内容(因为指向同一数据块)!!!
(2)删除硬链接
- 本质:仅删除
file2
这个文件名,i 节点(1234567
)和数据块仍存在。 - 效果:
- i 节点的硬链接计数从
2
变回 1
(file1
仍指向它)。
- 本质:i 节点的硬链接计数降为
0
,系统自动回收该 i 节点及其数据块。
4. i 节点 vs 文件名
行为 | 对 i 节点的影响 |
---|
创建文件 | 分配一个空闲 i 节点,初始化元数据,硬链接计数设为 1 。 |
创建硬链接 | i 节点的硬链接计数 +1 (多个文件名共享同一 i 节点)。 |
删除文件 | i 节点的硬链接计数 -1 ;若计数为 0 ,则释放 i 节点和数据块。 |
修改文件内容 | 更新 i 节点中的 mtime 和 ctime ,但 i 节点编号不变。 |
重命名文件 | 仅修改文件名记录,不影响 i 节点。 |
5. 关键结论
- i 节点是文件的唯一标识
- 文件名只是 i 节点的“别名”,同一个文件可以有多个文件名(硬链接)
- 删除文件的实际过程
rm
只是减少 i 节点的硬链接计数,计数为 0
时才会真正删除文件。
- 硬链接的限制
- 不能跨文件系统(因为 i 节点编号仅在同一个文件系统内唯一)。
- 不能对目录创建硬链接(防止循环引用导致文件系统混乱)。
6. 扩展命令
命令 | 作用 |
---|
ls -i | 显示文件的 i 节点编号。 |
df -i | 查看文件系统的 i 节点使用情况。 |
find / -inum 1234 | 通过 i 节点编号查找文件。 |
总结
- i 节点是文件的“身份证”,存储元数据但不含文件名或内容。
- 硬链接是多个文件名共享同一 i 节点,软链接(符号链接)则是==独立的文件(有自己的 i 节点),存储目标文件的路径(字符串)==
- 文件删除的本质是 减少 i 节点的硬链接计数,计数归零后系统才会回收资源。
文件编辑与流处理
ed编辑器
ed
是 Unix 历史上的里程碑式行编辑器,由 Ken Thompson 在 1970 年开发,其设计哲学深刻影响了后续工具(如 sed
、vim
)。以下是结合您提供的资料的系统性总结:
一、ed 的核心优势
极简主义
- 仅需 几 KB 内存 即可运行,适合救援模式或嵌入式系统。
- 无图形界面,所有操作通过命令驱动,可通过管道脚本化编辑。
正则表达式先驱
- 其正则语法(如
s/old/new/
)被 sed
、grep
、perl
等工具继承,成为业界标准。
高效处理
- 直接按行操作,避免全文件加载,处理大文件时速度显著优于现代编辑器。
二、核心命令详解(按功能分类)
1. 导航与显示
命令 | 作用 | 示例 |
---|
n | 跳转到第 n 行 | 5 → 跳转到第 5 行 |
.+3 | 相对行号(当前行+3) | .,.+5p → 显示后续 5 行 |
$ | 最后一行 | $p → 显示末行 |
,p | 显示全部内容 | 1,$p 等效 |
2. 编辑操作
命令 | 作用 | 结束符 |
---|
a | 当前行后追加 | 独占一行的 . |
i | 当前行前插入 | 同上 |
m,nd | 删除 m 到 n 行 | 无 |
u | 撤销最后一次编辑 | 仅支持一级撤销 |
3. 搜索与替换
命令 | 关键细节 | 示例 |
---|
/pattern/ | 向后搜索,循环至文件尾 | /main/ → 跳转到下一个 “main” |
?pattern? | 向前搜索,循环至文件头 | ?int? → 向上找 “int” |
s/old/new/[g] | g 表示全局替换 | s/cat/dog/g → 替换所有 “cat” |
& 占位符 | 引用匹配的文本 | s/big/very &/ → “big” → “very big” |
4. 文件操作
命令 | 说明 |
---|
w [file] | 保存(可另存为) |
q | 安全退出(未保存时提示) |
Q | 强制退出(不保存) |
!cmd | 临时执行 shell 命令(如 !ls ) |
三、经典使用场景
1. 脚本化编辑
1 2
| echo -e "1,\$s/foo/bar/g\nwq" | ed file.txt
|
2. 精准行操作
1 2
| echo -e "/debug/,+2d\nwq" | ed log.txt
|
3. 正则表达式测试
1 2
| echo -e "/error/,\$p\nq" | ed app.log
|
四、与现代工具对比
特性 | ed | sed /vim |
---|
交互性 | 极低(纯命令) | 中/高 |
学习曲线 | 陡峭 | 中等 |
适用场景 | 脚本化、救援模式 | 日常编辑 |
正则支持 | 基础 | 扩展(如 \d ) |
五、操作流程图解
1 2 3 4 5
| 启动 ed → [命令模式] ├─ 导航 (n, $, .) ├─ 编辑 (a/i, d, s) ├─ 搜索 (/pattern/, ?pattern?) └─ 保存退出 (wq)
|
六、为什么今天仍值得了解?
- 理解 Unix 哲学:
ed
是“工具链组合”思想的典范(与 grep
、awk
协同)。 - 应急修复:当系统仅剩
/bin/ed
可用时,它是最后的编辑手段。 - 历史教育:通过
ed
可直观看到现代编辑器的演进路径。
若需快速上手实用编辑,推荐 nano
或 vim
;但掌握 ed
如同学习汇编语言,能加深对计算本质的理解。
正则表达式
ed 正则表达式核心知识点
1. 元字符与转义
语法 | 作用 | 示例 |
---|
普通字符 | 匹配自身(如 a 、1 ) | cat → 匹配 “cat” |
\c | 取消字符 c 的特殊意义 | \* → 匹配字面 * |
^ | 行首(仅模式起始处有效) | ^hello → 行首的 “hello” |
$ | 行尾(仅模式结束处有效) | end$ → 行尾的 “end” |
. | 匹配任意单个字符 | a.c → “abc”, “a c” |
2. 字符类
语法 | 作用 | 示例 |
---|
[...] | 匹配括号内任一字符 | [aeiou] → 任意元音 |
[^...] | 匹配不在括号内的字符 | [^0-9] → 非数字 |
[a-z] | 字符范围(支持连字符 - ) | [A-Z] → 大写字母 |
3. 重复与分组
语法 | 作用 | 示例 |
---|
r* | 0 次或多次匹配 r | a* → “”, “a”, “aa” |
.* | 匹配任意长度字符串 | ^a.*z$ → “a开头到z结尾的整行” |
& | 替换时引用匹配的文本 | s/cat/&s/ → “cat”→”cats” |
4. 常用模式示例
模式 | 匹配目标 |
---|
^$ | 空行(开头即结尾) |
^# | 以 # 开头的行(如注释) |
\.$ | 以点号结尾的行 |
/[tT]est/ | “test” 或 “Test” |
[0-9][0-9]* | 至少一个数字 |
^[^a-zA-Z] | 不以字母开头的行 |
/thing.$/ | 以thing加任意符号结尾的行 |
5. 全局命令 (g/v
)
- 命令格式:m,ng/re/cmd,含义是从m行到n行中对于匹配re模式的行执行命令cmd. 如果作用范围是全文件(1,$),m、n可以省略
命令格式 | 作用 | 示例 |
---|
g/re/p | 打印匹配 re 的行 | g/error/p → 显示含 “error” 的行 |
g/re/d | 删除匹配 re 的行 | g/^$/d → 删除所有空行 |
g/re/s/old/new/ | 对匹配 re 的行替换 old →new | g/foo/s/bar/baz/ → 仅替换含 “foo” 的行中的 “bar” |
v/re/p | 取反操作(不匹配 re 的行) | v/^$/p → 打印非空行 |
6. 移动与复制
命令格式 | 作用 | 示例 |
---|
m,nmd | 将 m 到 n 行移动到 d 行后 | 2,4m5 → 2-4 行移到第 5 行后 |
m,ntd | 将 m 到 n 行复制到 d 行后 | 1,3t$ → 复制 1-3 行到文件末尾 |
g/^/m0 | 反转文件行序(每行移到第 0 行后) | 结果:最后一行变第一行 |
关键注意事项
- 贪婪匹配:
r*
是贪婪的(尽可能多匹配)。 - 转义特殊字符:如
\.
匹配字面点号,\\
匹配反斜杠。 - 全局命令范围:省略
m,n
时默认全文件(1,$
)。 - **替换中的
&
**:仅在 s///
右侧有效,代表匹配的全文。
ed 的正则为现代工具(如 sed
/grep
)奠定了基础,虽功能有限,但足够处理基础文本操作。
sed流编辑器
以下是结合参考文献对sed知识点的系统总结,关键部分标注引用来源:
sed核心特性
流编辑器本质
- 直接从
ed
发展而来,专为处理输入流设计(文件或管道数据) - 单次扫描输入流,高效但无法回溯已处理行(局限性)
- 默认输出到stdout且不修改原文件(需重定向保存结果)
基础语法结构
1
| sed [选项] '编辑命令1;编辑命令2' 输入文件
|
- 经典示例:
sed 's/UNIX/Linux/g' file
全局替换文本 - 支持多命令组合:
sed 's/foo/bar/; 10q' file
(替换+显示前10行)
常用操作场景
功能 | 命令示例 | 说明 |
---|
文本替换 | sed 's/old/new/g' file | 全局替换(加g 标志) |
行范围操作 | sed '10q' file | 显示前10行(q 退出命令) |
模式过滤 | sed -n '/pattern/p' file | 仅显示匹配行(-n 关闭默认输出,等效grep ) |
目录列表过滤 | `ls -l | sed -n ‘/^d/p’` |
多模式范围输出 | sed -n '/start/,/end/p' file | 打印两个模式间的所有行(如/David/,/Emily/p ) |
关键选项与限制
选项
-n
:抑制默认输出,需显式用p
命令打印-e
:指定多个编辑命令(如sed -e 's/a/b/' -e 's/c/d/'
)
局限性
- 无法行运算:如
$-1d
非法,因sed是单向流处理器 - 无交互模式:所有操作需通过命令预设
与管道的协同
动态处理流数据:
组合其他命令:
1
| grep "error" log.txt | sed 's/ERROR/CRITICAL/g'
|
扩展应用
批量编辑文件:
1
| sed -i.bak 's/old/new/g' *.txt
|
条件删除:
设计哲学
- UNIX工具链思维:专注单一功能(文本转换),通过管道与其他工具(如
grep
、awk
)协作[][6] - 高效性:单次流处理比交互式编辑器更适合自动化任务[][6]
通过掌握这些核心模式,可高效完成90%的文本处理需求。进阶学习可参考GNU sed手册[6]中的正则表达式和保持空间(hold space)技巧。
grep过滤器
grep
是 Linux/Unix 中最强大的文本过滤工具之一,常与管道符 |
和其他命令(如 ls
、sed
、sort
)结合使用
1. grep
基础语法
- 核心功能:从文件或输入流中筛选包含指定模式的行。
- 常用选项:
-i
:忽略大小写(如 grep -i "error" log.txt
)。-v
:反向匹配(显示不包含模式的行)。-n
:显示匹配行的行号。-c
:统计匹配行的数量。-r
:递归搜索目录(如 grep -r "main" /src
)。
示例 1:搜索文件内容
- 作用:在
sig.c
文件中查找以 void
开头的行。
示例 2:过滤目录
- 作用:列出当前目录下的子目录(不包括文件)。
- 原理:
ls -l
的输出中,目录行以 d
开头(如 drwxr-xr-x
)。^d
匹配行首的 d
字符。
示例 3:提取目录名
1
| ls -l | grep '^d' | sed 's/.* //'
|
- 作用:仅输出子目录名(去掉权限、时间等冗余信息)。
- 分步解析:
ls -l | grep '^d'
:筛选目录行。sed 's/.* //'
:删除行中最后一个空格前的所有内容(保留目录名)。
3. grep
家族对比
命令 | 全称 | 特点 |
---|
grep | Global Regular Expression Print | 基础版,支持基本正则表达式(BRE)。 |
egrep | Extended GREP | 支持扩展正则表达式(ERE),如 + 、? 、` |
fgrep | Fixed-string GREP | 仅匹配固定字符串(不支持正则),但处理大文件时速度最快。 |
典型场景
egrep
的扩展功能:1
| egrep 'error|warn' log.txt
|
fgrep
的高效性:1
| fgrep -c "404" access.log
|
4. 结合其他过滤器
4.1 sort
(排序)
1 2
| ls | sort grep "error" log.txt | sort -u
|
4.2 head
/ tail
(首尾行)
1 2
| grep "Exception" server.log | tail -5 grep "login" auth.log | head -3
|
4.3 组合实战
1 2
| grep -o "ERROR: .*" app.log | sort | uniq -c | sort -nr | head -5
|
- 步骤分解:
grep -o
:提取所有 ERROR: xxx
内容。sort
:排序以便 uniq
统计。uniq -c
:计数。sort -nr
:按计数降序。head -5
:显示前5条。
总结
grep
:文本过滤的瑞士军刀,核心是模式匹配。- 管道组合:与
sed
、sort
、head
/tail
联动可解决复杂问题。 - 选择工具:
- 简单搜索 →
grep
或 fgrep
。 - 复杂正则 →
egrep
。 - 需排序/统计 → 结合
sort | uniq -c
。