本文为在B站上学习linux命令的学习笔记,视频出处为https://www.bilibili.com/video/BV1244y1e73a?p=23&spm_id_from=pageDrive 如果有侵权行为,请联系我删除
sed 是一种新型的,非交互式的编辑器。它能执行与编辑器 vi 和 ex 相同的编辑任务。sed 编辑器没有提供交互式使用方式,使用者只能在命令行输入编辑命令、指定文件名,然后在屏幕上查看输出。sed 编辑器没有破坏性,它不会修改文件,除非使用 shell 重定向来保存输出结果。默认情况下,所有的输出行都被打印到屏幕上。
sed 编辑器逐行处理文件(或输入),并将输出结果发送到屏幕。sed 的命令就是在 vi和 ed/ex 编辑器中见到的那些。sed 把当前正在处理的行保存在一个临时缓存区中,这个缓存区称为模式空间或临时缓冲。sed 处理完模式空间中的行后(即在该行上执行 sed 命令后),
就把该行发送到屏幕上(除非之前有命令删除这一行或取消打印操作)。sed 每处理完输入文件的最后一行后,sed 便结束运行。sed 把每一行都存在临时缓存区中,对这个副本进行编辑,所以不会修改或破坏源文件。如图 1:sed 处理过程。
从上图可以看出 sed 不是破坏性的,它不会修改正在编辑的文件。
sed 命令行格式为: sed [选项] ‘command’ 输入文本
Sed 命令在没有给定的位置时,默认会处理所有行;
Sed 支持一下几种地址类型:
元字符 | 功 能 | 示 例 | 示例的匹配对象 |
---|---|---|---|
^ | 行首定位符 | /^love/ | 匹配所有以 love 开头的行 |
$ | 行尾定位符 | /love$/ | 匹配所有以 love 结尾的行 |
. | 匹配除换行外的单个字符 | /l..e/ | 匹配包含字符 l、后跟两个任意字符、再跟字母 e 的行 |
* | 匹配零个或多个前导字符 | /*love/ | 匹配在零个或多个空格紧跟着模式 love 的行 |
[] | 匹配指定字符组内任一字符 | /[Ll]ove/ | 匹配包含 love 和 Love 的行 |
[^] | 匹配不在指定字符组内任一字符 | /[^A-KM-Z]ove/ | 匹配包含 ove,但 ove 之前的那个字符不在 A 至 K 或 M 至 Z 间的行 |
\(..\) | 保存已匹配的字符 | ||
& | 保存查找串以便在替换串中引用 | s/love/**&**/ | 符号&代表查找串。字符串 love将替换前后各加了两个**的引用,即 love 变成**love** |
\< | 词首定位符 | /\匹配包含以 love 开头的单词的行 |
|
\> | 词尾定位符 | /love\>/ | 匹配包含以 love 结尾的单词的行 |
x\{m\} | 连续 m 个 x | /o\{5\}/ | 分别匹配出现连续 5 个字母 o、至少 5 个连续的 o、或5~10 个连续的 o 的行 |
x\{m,\} | 至少 m 个 x | /o\{5,\}/ | |
x\{m,n\} | 至少 m 个 x,但不超过 n 个 x | /o\{5,10\}/ | 分别匹配出现连续 5 个字母 o、至少 5 个连续的 o、或 5~10 个连续的 o 的行 |
选项 | 说明 |
---|---|
-n | 使用安静模式,在一般情况所有的 STDIN 都会输出到屏幕上,加入-n 后只打印被 sed 特殊处理的行 |
-e | 多重编辑,且命令顺序会影响结果 |
-f | 指定一个 sed 脚本文件到命令行执行, |
-r | Sed 使用扩展正则 |
-i | 直接修改文档读取的内容,不在屏幕上输出 |
sed 操作命令告诉 sed 如何处理由地址指定的各输入行。如果没有指定地址,sed 就会处理输入的所有的行。
命令选项
命令 | 说 明 |
---|---|
a | 在当前行后添加一行或多行 |
c | 用新文本修改(替换)当前行中的文本 |
d | 删除行 |
i | 在当前行之前插入文本 |
h | 把模式空间里的内容复制到暂存缓存区 |
H | 把模式空间里的内容追加到暂存缓存区 |
g | 取出暂存缓冲区里的内容,将其复制到模式空间,覆盖该处原有内容 |
G | 取出暂存缓冲区里的内容,将其复制到模式空间,追加在原有内容后面 |
l | 列出非打印字符 |
p | 打印行 |
n | 读入下一输入行,并从下一条命令而不是第一条命令开始处理 |
q | 结束或退出 sed |
r | 从文件中读取输入行 |
! | 对所选行意外的所有行应用命令 |
s | 用一个字符串替换另一个 |
替换标志
表 4.替换标志
标识 | 含义 |
---|---|
g | 在行内进行全局替换 |
p | 打印行 |
w | 将行写入文件 |
x | 交换暂存缓冲区与模式空间的内容 |
y | 将字符转换为另一字符(不能对正则表达式使用 y 命令) |
遇到语法错误时,sed 会向标准错误输出发送一条相当简单的报错信息。但是,如果 sed判断不出错在何处,它会“断章取义”,给出令人迷惑的报错信息。如果没有语法错误,sed将会返回给 shell 一个退出状态,状态为 0 代表成功,为非 0 整数代表失败。
Sed 测试实例
下面这组范例展示了如何使用 sed,包括如何使用它的选项、命令和正则表达式。记住sed 不是破坏性的,它不会修改正在编辑的文件,除非重定向它的输出结果。
测试实例
下面给出测试文件 ceshi.txt 作为输入文件。
northwest NW Charles Main 3.0 .98 3 34
western WE Sharon Gray 5.3 .97 5 23
southwest SW Lewis Dalsass 2.7 .8 2 18
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
eastern EA TB Savage 4.4 .84 5 20
northeast NE AM Main Jr. 5.1 .94 3 13
north NO Margot Weber 4.5 .89 5 9
central CT Ann Stephens 5.7 .94 5 13
命令 p 是打印命令,用于显示模式缓存区的内容。默认情况下,sed 把输入行打印在屏幕上,选项-n 用于取消默认打印操纵。当选项-n 和命令 p 同时出现时,sed 可打印选定的内
容。
[root@yum test]# sed '/north/p' sed.txt
northwest NW Charles Main 3.0 .98 3 34
northwest NW Charles Main 3.0 .98 3 34
western WE Sharon Gray 5.3 .97 5 23
southwest SW Lewis Dalsass 2.7 .8 2 18
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
eastern EA TB Savage 4.4 .84 5 20
northeast NE AM Main Jr. 5.1 .94 3 13
northeast NE AM Main Jr. 5.1 .94 3 13
north NO Margot Weber 4.5 .89 5 9
north NO Margot Weber 4.5 .89 5 9
central CT Ann Stephens 5.7 .94 5 13
说明:
默认情况下,sed 把所有输入行都打印在标准输出上。如果在某一行匹配到 north,sed就把该行另外打印一遍。
案例 2:
[root@yum test]# sed -n '/north/p' sed.txt
northwest NW Charles Main 3.0 .98 3 34
northeast NE AM Main Jr. 5.1 .94 3 13
north NO Margot Weber 4.5 .89 5 9
说明:
默认情况下,sed 打印当前缓存区中的输入行。命令 p 指示 sed 将再次打印该行。选项-n 取消 sed 取消默认打印操作。选线-n 和命令配合使用,模式缓冲区内的输入行,只被打印一次。如果不指定-n 选项,sed 就会像上例中那样,打印出重复的行。如果指定了-n,则sed 只打印包含模式 north 的行。
命令 d 用于删除输入行。sed 先将输入行从文件复制到模式缓存区,然后对该行执行 sed命令,最后将模式缓存区的内容显示在屏幕上。如果发出的是命令 d,当前模式缓存区的输入行会被删除,不被显示。
[root@yum test]# sed '3d' sed.txt
northwest NW Charles Main 3.0 .98 3 34
western WE Sharon Gray 5.3 .97 5 23
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
eastern EA TB Savage 4.4 .84 5 20
northeast NE AM Main Jr. 5.1 .94 3 13
north NO Margot Weber 4.5 .89 5 9
central CT Ann Stephens 5.7 .94 5 13
说明:
删除第 3 行。默认情况下,其余的行都被打印到屏幕上。
[root@yum test]# sed '3,$d' sed.txt
northwest NW Charles Main 3.0 .98 3 34
western WE Sharon Gray 5.3 .97 5 23
说明:
删除从第三行到最后一行内容,剩余各行被打印。地址范围是开始第 3 行,结束最后一行。
[root@yum test]# sed '/north/d' sed.txt
western WE Sharon Gray 5.3 .97 5 23
southwest SW Lewis Dalsass 2.7 .8 2 18
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
eastern EA TB Savage 4.4 .84 5 20
central CT Ann Stephens 5.7 .94 5 13
说明:所有包含模式 north 的行都被动删除,其余行被打印。
命令 s 是替换命令。替换和取代文件中的文本可以通过 sed 中的 s 来实现,s 后包含在斜杠中的文本是正则表达式,后面跟着的是需要替换的文本。可以通过 g 标志对行进行全局替换
[root@yum test]# sed 's/west/north/g' sed.txt
northnorth NW Charles Main 3.0 .98 3 34
northern WE Sharon Gray 5.3 .97 5 23
southnorth SW Lewis Dalsass 2.7 .8 2 18
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
eastern EA TB Savage 4.4 .84 5 20
northeast NE AM Main Jr. 5.1 .94 3 13
north NO Margot Weber 4.5 .89 5 9
central CT Ann Stephens 5.7 .94 5 13
说明:
s 命令用于替换。命令末端的 g 表示在行内全局替换;也就是说如果每一行里出现多个west,所有的 west 都会被替换为 north。如果没有 g 命令,则只将每一行的第一 west 替换为 north。
[root@yum test]# sed -n 's/^west/north/p' sed.txt
northern WE Sharon Gray 5.3 .97 5 23
说明:
s 命令用于替换。选线-n 与命令行末尾的标志 p 结合,告诉 sed 只打印发生替换的那些行;也就是说,如果只有在行首找到 west 并替换成 north 时才会打印此行。
[root@yum test]# sed 's/[0-9][0-9]$/&.5/' sed.txt
northwest NW Charles Main 3.0 .98 3 34.5
western WE Sharon Gray 5.3 .97 5 23.5
southwest SW Lewis Dalsass 2.7 .8 2 18.5
southern SO Suan Chin 5.1 .95 4 15.5
southeast SE Patricia Hemenway 4.0 .7 4 17.5
eastern EA TB Savage 4.4 .84 5 20.5
northeast NE AM Main Jr. 5.1 .94 3 13.5
north NO Margot Weber 4.5 .89 5 9
central CT Ann Stephens 5.7 .94 5 13.5
说明:
当“与”符号(&)用在替换串中时,它代表在查找串中匹配到的内容时。这个示例中所有以 2 位数结尾的行后面都被加上.5。
[root@yum test]# sed -n 's/Hemenway/Jones/gp' sed.txt
southeast SE Patricia Jones 4.0 .7 4 17
说明:
文件中出现的所有的 Hemenway 都被替换为 Jones,只有发生变化的行才会打印出来。选项-n 与命令 p 的组合取消了默认的输出。标志 g 的含义是表示在行内全局替换。
[root@yum test]# sed 's/\(Mar\)got/\1linanne/p' sed.txt
northwest NW Charles Main 3.0 .98 3 34
western WE Sharon Gray 5.3 .97 5 23
southwest SW Lewis Dalsass 2.7 .8 2 18
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
eastern EA TB Savage 4.4 .84 5 20
northeast NE AM Main Jr. 5.1 .94 3 13
north NO Marlinanne Weber 4.5 .89 5 9
north NO Marlinanne Weber 4.5 .89 5 9
central CT Ann Stephens 5.7 .94 5 13
说明:
包含在圆括号里的模式 Mar 作为标签 1 保存在特定的寄存器中。替换串可以通过\1 来引用它。则 Margot 被替换为 Marlinane。
[root@yum test]# sed 's#3#88#g' sed.txt
northwest NW Charles Main 88.0 .98 88 884
western WE Sharon Gray 5.88 .97 5 288
southwest SW Lewis Dalsass 2.7 .8 2 18
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
eastern EA TB Savage 4.4 .84 5 20
northeast NE AM Main Jr. 5.1 .94 88 188
north NO Margot Weber 4.5 .89 5 9
central CT Ann Stephens 5.7 .94 5 188
说明:
紧跟在 s 命令后的字符就是查找串和替换串之间的分隔符。分隔符默认默认为正斜杠,但可以改变。无论什么字符(换行符,反斜线除外),只要紧跟在 s 命令,就成了新的串分隔符。这个方法在查找包含正斜杠模式时很管用,例如查找路径名或生日。
行的范围从文件中的一个地址开始,在另一个地址结束。地址范围可以是行号(例如5,10),正则表达式(例如/Dick/和/Joe/),或者两者的结合(例如/north/,$)范围是闭合的——包含开始条件的行,结束条件的行,以及两者之间的行。如果结束条件无法满足,就会一直操作到文件结尾。如果结束条件满足,则继续查找满足开始条件的位置,范围重新开始。
[root@yum test]# sed -n '/west/,/east/p' sed.txt
northwest NW Charles Main 3.0 .98 3 34
western WE Sharon Gray 5.3 .97 5 23
southwest SW Lewis Dalsass 2.7 .8 2 18
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
说明:
打印模式 west 和 east 之间所有的行。如果 west 出现在 east 之后的某一行,则打印的范围从 west 所在行开始,到下一个出现 east 的行或文件的末尾(如果前者未出现)。图中用箭头表示出了该范围。
[root@yum test]# sed -n '5,/northeast/p' sed.txt
southeast SE Patricia Hemenway 4.0 .7 4 17
eastern EA TB Savage 4.4 .84 5 20
northeast NE AM Main Jr. 5.1 .94 3 13
说明:
打印从第 5 行开始第一个以 northeast 开头的行之间的所有行。
[root@yum test]# sed '/west/,/east/s/$/**VACA**/' sed.txt
northwest NW Charles Main 3.0 .98 3 34**VACA**
western WE Sharon Gray 5.3 .97 5 23**VACA**
southwest SW Lewis Dalsass 2.7 .8 2 18**VACA**
southern SO Suan Chin 5.1 .95 4 15**VACA**
southeast SE Patricia Hemenway 4.0 .7 4 17**VACA**
eastern EA TB Savage 4.4 .84 5 20
northeast NE AM Main Jr. 5.1 .94 3 13
north NO Margot Weber 4.5 .89 5 9
central CT Ann Stephens 5.7 .94 5 13
说明:
修改从模式 wast 和 east 之间的所有行,将各行的行尾($)替换为字符串VACA。换行符被移到新的字符串后面。
-e 命令是编辑命令,用于 sed 执行多个编辑任务的情况下。在下一行开始编辑前,所有的编辑动作将应用到模式缓存区的行上。
[root@yum test]# sed -e '1,3d' -e 's/Hemenway/Jones/' sed.txt
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Jones 4.0 .7 4 17
eastern EA TB Savage 4.4 .84 5 20
northeast NE AM Main Jr. 5.1 .94 3 13
north NO Margot Weber 4.5 .89 5 9
central CT Ann Stephens 5.7 .94 5 13
说明:选项-e 用于进行多重编辑。第一重编辑编辑删除第 1~3 行。第二重编辑将Hemenway 替换为 Jones。因为是逐行进行这两行编辑(即这两个命令都在模式空间的当前行上执行),所以编辑命令的顺序会影响结果。例如,如果两条命令都执行的是替换,前一次替换会影响后一次替换。
a 命令是追加命令,追加将新文本到文件中当前行(即读入模式的缓存区行)的后面。不管是在命令行中,还是在 sed 脚本中,a 命令总是在反斜杠的后面。
[root@yum test]# sed '/^north /a Hello,World!' sed.txt
northwest NW Charles Main 3.0 .98 3 34
western WE Sharon Gray 5.3 .97 5 23
southwest SW Lewis Dalsass 2.7 .8 2 18
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
eastern EA TB Savage 4.4 .84 5 20
northeast NE AM Main Jr. 5.1 .94 3 13
north NO Margot Weber 4.5 .89 5 9
Hello,World!
central CT Ann Stephens 5.7 .94 5 13
说明:
命令 a 用于追加。字符串 Hello,World!被加在以 north 开头,north 后面跟一个空格的各行之后。如果要追加的内容超过一行,则除最后一行外,其他各行都必须以反斜杠结尾。
i 命令是插入命令,类似于 a 命令,但不是在当前行后增加文本,而是在当前行前面插入新的文本,即刚读入缓存区模式的行。
[root@yum test]# sed '/eastern/i Hello,World! \
> -----------------------------------' sed.txt
northwest NW Charles Main 3.0 .98 3 34
western WE Sharon Gray 5.3 .97 5 23
southwest SW Lewis Dalsass 2.7 .8 2 18
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
Hello,World!
-----------------------------------
eastern EA TB Savage 4.4 .84 5 20
northeast NE AM Main Jr. 5.1 .94 3 13
north NO Margot Weber 4.5 .89 5 9
central CT Ann Stephens 5.7 .94 5 13
说明:
命令 i 是插入命令。如果在某一行匹配到模式 eastern,i 命令就在该行的上方插入命令中插入反斜杠后面后的文本。除了最后一行,
c 命令是修改命令。sed 使用该命令将已有的文本修改成新的文本。旧文本被覆盖。
[root@yum test]# sed '/eastern/c Hello,World! \
-----------------------------------' sed.txt
northwest NW Charles Main 3.0 .98 3 34
western WE Sharon Gray 5.3 .97 5 23
southwest SW Lewis Dalsass 2.7 .8 2 18
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
Hello,World!
-----------------------------------
northeast NE AM Main Jr. 5.1 .94 3 13
north NO Margot Weber 4.5 .89 5 9
central CT Ann Stephens 5.7 .94 5 13
说明:
c 命令是修改命令。该命令将完整地修改在模式缓冲区行的当前行。如果模式 eastern被匹配,c 命令将其后的文本替换包含 eastern 的行。
n 命令表示下一条命令。sed 使用该命令获取输入文件的下一行,并将其读入到模式缓冲区中,任何 sed 命令都将应用到匹配行,紧接着的下一行上。
[root@yum test]# sed '/eastern/{n;s/AM/Archie/;}' sed.txt
northwest NW Charles Main 3.0 .98 3 34
western WE Sharon Gray 5.3 .97 5 23
southwest SW Lewis Dalsass 2.7 .8 2 18
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
eastern EA TB Savage 4.4 .84 5 20
northeast NE Archie Main Jr. 5.1 .94 3 13
north NO Margot Weber 4.5 .89 5 9
central CT Ann Stephens 5.7 .94 5 13
说明:
如果在某一行匹配到模式 eastern,n 命令就指示 sed 用下一个输入行(即包含 AM Main Jr 的那行)替换模式空间中的当前行,并用 Archie 替换 AM,然后打印该行,再继续往下处理。
y 命令表示转换。该命令与 tr 命令相似,字符按照一对一的方式从左到右进行转换。例如 y/abc/ABC/,会把小写字母转换成大写字母,a–>A,b–>B,c–>C。
[root@yum test]# sed
'1,3y/abcdefghijklmnopqrstuvwxyz/ABCDEFGHIJKLMNOPQRSTUVWXYZ/' sed.txt
NORTHWEST NW CHARLES MAIN 3.0 .98 3 34
WESTERN WE SHARON GRAY 5.3 .97 5 23
SOUTHWEST SW LEWIS DALSASS 2.7 .8 2 18
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
eastern EA TB Savage 4.4 .84 5 20
northeast NE AM Main Jr. 5.1 .94 3 13
north NO Margot Weber 4.5 .89 5 9
central CT Ann Stephens 5.7 .94 5 13
说明:
y 命令把 1~3 行中所有的小写命令字母都转换成了大写。正则表达式元字符对 y 命令不起作用。与替分隔符一样,斜杠可以被替换成其他字符。
q 命令表示退出命令。该命令将导致 sed 程序退出,且不再进行其他的处理。
[root@yum test]# sed '5q' sed.txt
northwest NW Charles Main 3.0 .98 3 34
western WE Sharon Gray 5.3 .97 5 23
southwest SW Lewis Dalsass 2.7 .8 2 18
southern SO Suan Chin 5.1 .95 4 15
southeast SE Patricia Hemenway 4.0 .7 4 17
说明:
打印完第 5 行之后,q 让 sed 程序退出。
[root@yum test]# sed '/Lewis/{ s/Lewis/Joseph/;q; }' sed.txt
northwest NW Charles Main 3.0 .98 3 34
western WE Sharon Gray 5.3 .97 5 23
southwest SW Joseph Dalsass 2.7 .8 2 18
说明:
在某行匹配到模式 Lewis 时,s 表示先用 Joseph 替换 Lewis,然后 q 命令让 sed 退出。
在实际生产中,在修改配置文件的时候,有一些空格、空行、带“#”开头的注释都要删除或替换,下面为大家介绍几个实用的例子
[root@yum test]# cat sed2.txt
tody is nice day
you can walk out on the street
it will be import to you
[root@yum test]# sed 's/^[ ]*//' sed2.txt
tody is nice day
you can walk out on the street
it will be import to you
[root@yum test]#
或者
[root@yum test]# sed 's/^[[:space:]]*//' sed2.txt
tody is nice day
you can walk out on the street
it will be import to you
[root@yum test]#
[root@yum tmp]# grep -viE "^#|^$" ssh_config
Host *
GSSAPIAuthentication yes
ForwardX11Trusted yes
SendEnv LANG LC_CTYPE LC_NUMERIC LC_TIME LC_COLLATE LC_MONETARY LC_MESSAGES
SendEnv LC_PAPER LC_NAME LC_ADDRESS LC_TELEPHONE LC_MEASUREMENT
SendEnv LC_IDENTIFICATION LC_ALL LANGUAGE
SendEnv XMODIFIERS
用 sed 方法
[root@yum tmp]# grep -viE "^#|^$" ssh_config
Host *
GSSAPIAuthentication yes
ForwardX11Trusted yes
SendEnv LANG LC_CTYPE LC_NUMERIC LC_TIME LC_COLLATE LC_MONETARY LC_MESSAGES
SendEnv LC_PAPER LC_NAME LC_ADDRESS LC_TELEPHONE LC_MEASUREMENT
SendEnv LC_IDENTIFICATION LC_ALL LANGUAGE
SendEnv XMODIFIERS
[root@yum test]# cat sed2.txt
1tody is nice day
2you can walk out on the street
13it will be import to you
[root@yum test]# sed 's/^[0-9][0-9]*//g' sed2.txt
tody is nice day
you can walk out on the street
it will be import to you
本章内容总结了 sed 命令的用法,前面部分是 sed 命令的语法,后面部分则主要以实际案例来说明 sed 的用法,最后面一点介绍了 sed 命令在生产实践中的运用。所谓学为练,练为战,希望大家能够将 sed 命令勤加练习,必将会在工作中有所用途,尤其是频繁的分析日志文件,Awk+Sed 是比较好的组合。最后希望本文对大家有所帮助,真正达到熟练的程度这就靠大家在工作中归纳总结了。