Linux sed 命令 - 流式文本匹配替换删除插入工具
sed 命令(英文全称为 Stream Editor)是 Linux / Unix 系统中经典的流式编辑器,主要是对流式文本内容逐行进行处理,可以按照正则表达式匹配内容、替换内容、删除内容、插入内容等操作,它以非交互方式处理文本内容,是处理文本内容的一款非常好用的工具。
sed 命令语法
如下给出包含全部选项的 sed 命令的语法结构:
sed [-V] [--version] [--help] [-n] [--quiet] [--silent]
[-l N] [--line-length=N] [-u] [--unbuffered]
[-E] [-r] [--regexp-extended]
[-e script] [--expression=script]
[-f script-file] [--file=script-file]
[script-if-no-other-script]
[file...]
语法的简单解释说明:
- 当不提供
-e/-f时,如果包含非选项的参数[script-if-no-other-script]该内容为脚本 [file...]: 需要处理的文件,可以同时指定多个文件,如果非指定时从标准输入读取内容
sed 常用命令示例
如下给出一些关于 sed 命令的使用示例,需要结合地址匹配规则和地址指令来学习。
执行全局替换
使用 s/regexp/replacement/ 在全局范围内容使用正则表达式替换内容:
sed 's/old/new/g' test.txt
该示例将文件中所有 old 替换为 new
只打印奇数行
使用 -n 选项关闭自动打印,使用 1~2p 打印奇数行:
sed -n '1~2p' test.txt
命令解释说明:
-n: 关闭自动打印1~2:first~step地址类型,匹配第一行,以及从第一行后面的行开始从 1 计数,为 2 的倍数的行,即 3, 5, 7 ...p为输出当前模式空间的所有行。
删除内容行
使用 -E 选项使用扩展的正则表达式,可以使用 |、^、$ 等符号:
sed -E '/^#|^$/d' config.conf
命令解释说明:
/^#|^$/: 匹配以#开头的行或者匹配^$的行(空行)d: 为删除内容的地址命令
行前插入 / 行尾追加
如下示例在行前插入内容和在行尾追加内容:
sed '3i\insert line' test.txt
sed '$a\append line' test.txt
命令解释说明:
3i\insert line:3寻址第3行,i\在前面插入内容,insert line需要插入的内容$a\append line:$寻址第后一行,a\在后面追加内容,append line需要追加的内容
指定行范围替换
该示例在指定的范围行内替换内容:
sed '2,5s/enable/disable/' test.txt
命令解释说明:
2,5: 双地址寻址,从第2行到第5行。s/enable/disable/: 执行正则表达式替换,把enable替换为disable
字符一一转换
使用 y/source/dest/ 形式实现字符集的替换:
sed 'y/abc/ABC/' test.txt
读取到指定行后退出
寻址到指定行,使用 q 地址指令退出 sed 命令:
sed '5q' test.txt
sed 地址匹配规则
基础规则
- 无地址:指令对所有行执行指定的操作
- 单地址:只对匹配的行执行指定的操作
- 双地址
addr1,addr2:对从 addr1 到 addr2 的范围内的行执行指定的操作 !取反:地址后加!,指令对匹配的行之外的行执行指定多的操作
地址类型
| 地址格式 | 功能说明 |
|---|---|
| 数字 | 匹配指定行号的行(当使用多文件时,行号连续计数,使用 -s 选项分开计数) |
first~step | 从 first 行开始,每隔 step 行匹配一次 |
$ | 匹配最后的一行 |
/regexp/ | 匹配与 regexp 正则表达式匹配的行 |
\cregexpc | 使用自定义分隔符 c 匹配与 regexp 正则表达式匹配的行,c 可以是任意字符 |
GNU 扩展地址格式
| 地址格式 | 功能说明 |
|---|---|
0,addr2 | 从第一个匹配的状态到 addr2 |
addr1,+N | 匹配 addr1 及其之后 N 行 |
addr1,~N | 匹配从 addr1 开始到下一个行号为 N 的倍数的行 |
sed 正则表达式规则
- 支持 POSIX 基础正则表达式(BRE),
\n匹配换行符,同样支持\a、\t等转义字符 -E/-r启用扩展正则表达式(ERE),现已纳入 POSIX 标准- 替换中:使用
&引用匹配的完整的字符串,使用\1–\9引用对应的捕获组
sed 地址指令详解
sed 命令的指令按寻址能力的不同分为三类:无地址指令、单地址指令、地址范围指令,使用地址规则匹配内容后,使用地址指令来执行相应的操作。
无地址指令
无地址指令会在全局范围内执行操作:
| 指令格式 | 功能说明 |
|---|---|
:label | 配合 b / t 选项使用的标签 |
#comment | 注释行的内容,当使用 -e 选项时到脚本片段的结束 |
} | {} 指令代码块的结束标志 |
零/单地址指令
零/单地址指令在指定的行内执行操作:
| 指令格式 | 功能说明 |
|---|---|
= | 打印当前行号 |
a \text | 在指定行的后面追加文本,文本中的每个换行前需要添加反斜杠 |
i \text | 在指定行的前面插入文本,文本中的每个换行前需要添加反斜杠 |
q [exit-code] | 立即退出 sed,未禁用自动打印则输出当前行, exit-code 是GNU 的扩展参数 |
Q [exit-code] | 立即退出 sed,不输出任何内容,exit-code 是GNU 的扩展参数 |
r filename | 读取文件全部内容并追加到匹配行的后面 |
R filename | 每次调用仅读取文件中的一行内容,追加到匹配行的后面,该选项是 GNU 扩展 |
地址范围指令
地址范围指令在匹配的地址范围内执行操作:
| 指令格式 | 功能说明 |
|---|---|
{ | 指令代码块的开始标志 |
b label | 无条件跳转到标签 label,当省略标签时则跳转到脚本的末尾 |
c \text | 用指定文本替换选中的行 |
d | 删除模式空间,开始下一轮循环 |
D | 删除模式空间中直到第一个换行符的内容,不读取新行,直接重启循环 |
h / H | 复制 / 追加模式空间中的内容到保存空间 |
g / G | 复制 / 追加保存空间的内容到模式空间 |
l | 以「无歧义可视形式」打印当前行,会显示不可见字符 |
l width | 按指定宽度换行显示内容,以「无歧义可视形式」打印当前行,该选项是 GNU 扩展功能 |
n / N | 读取 / 追加下一行的输入内容到模式空间 |
p | 打印当前模式空间的全部内容 |
P | 仅打印模式空间中第一行的内容 |
s/regexp/replacement/ | 把匹配正则表达式 regexp 的内容,替换为 replacement,在 replacement 中可以使用 & 来代表匹配内容,\1-\9 代表匹配到的分组 |
t label | 如果自上次读取输入行或上次执行 t 或 T 命令以来,替换成功则跳转到标签 label,如果未指定标签则跳转到脚本末尾 |
T label | 如果自上次读取输入行或上次执行 t 或 T 命令以来,替换失败则跳转到标签 label,该选项是 GNU 扩展功能 |
w filename | 将当前模式空间写入到文件中 |
W filename | 将模式空间中的第一行写入文件,该选项是 GNU 扩展功能 |
x | 交换模式空间与保存空间中的内容 |
y/source/dest/ | 将 source 中的字符一一映射转换为 dest 中的字符 |
[!TIP]
模式空间即当前正在处理的行。
sed 选项详解
如下给出 sed 命令的所有的选项的详细解释说明:
| 选项 | 功能说明 |
|---|---|
-V, --version | 显示版本信息并退出 |
--help | 显示帮助信息并退出 |
-n, --quiet, --silent | 禁止自动打印模式空间,只显式输出 |
-l N, --line-length=N | 设置 l 指令的换行长度 |
-u, --unbuffered | 使用无缓冲模式,从文件加载最少的内容、频繁的刷新输出缓冲区 |
-E, -r, --regexp-extended | 使用扩展正则表达式 |
-e script, --expression=script | 指定执行的脚本,可以同时使用多个 -e 选项 |
-f file, --file=file | 从文件 file 读取脚本 |
-i[SUFFIX], --in-place[=SUFFIX] | 在原文件中修改文件;提供后缀 SUFFIX 则先备份原文件 |
-s, --separate | 多个文件独立处理,不把多个文件中的行进行连续计数 |
-z, --null-data | 以 NUL 字符作为行分隔符 |
--debug | 调试模式,标注执行过程 |
--follow-symlinks | 在原文件中修改时跟随符号链接 |
--posix | 禁用所有的 GNU 扩展,严格遵循 POSIX 标准 |
--sandbox | 启用沙盒模式,禁用 e/r/w 等高风险的指令 |
结语
sed 命令是 Linux / Unix 系统中功能比较全面的流式文本编辑工具,可以执行按照正则表达式匹配内容、替换内容、删除内容、插入内容等操作。本文介绍了 sed 命令的指令集、地址规则、正则语法、使用示例以及所有选项的详细解释说明,内容非常的全面。