sed命令详解

一、基础篇

1、sed工作原理

sed工作的过程是先从文件中读取一行内容到模式空间里即sed专属的缓存空间,然后判断这行内容是否是需要处理的内容,如果不是就继续从文件中读取下一行,否则对改行内容进行相应处理后输出,然后继续读取下一行进行判断或处理,直到文件最后一行处理完毕整个过程结束。

2、sed命令使用说明

sed命令格式如下:

sed  参数  功能选项  文件名或其他标准输入

sed参数如下:

-i  修改文件内容

-n  取消默认输出

sed功能选项如下:

a  追加内容到指定行后

i  插入内容到指定行前

d  删除指定行

c  用新行替换旧行(不常用)

s  对每一行第一次匹配到的内容进行替换,配合标志g可以将一行中所有匹配到的内容进行替换

p  输出指定内容,默认会输出2次匹配到的内容

sed指定操作行的格式有以下几种:

10             匹配第十行
10,20                匹配第十行到第二十行
10,+20            匹配第十行到第三十行(10+20)
1~2              匹配第一行开始的奇数行
10,$             匹配第十行到最后一行
/oldboy/             匹配有oldboy的行
/oldboy/,/Alex/        匹配有oldboy的行到有Alex的行
/oldboy/,$          匹配有oldboy的行到最后一行
/oldboy/,10           匹配有oldboy的行到第十行,如果前十行没有匹配到有oldboy的行会对后面匹配到有oldboy的行进行操作
1,/Alex/           匹配第一行到有Alex的行
/oldboy/,+2           匹配有oldboy的行及之后的两行

sed s 替换脚本命令

此命令的基本格式为:

[address]s/pattern/replacement/flags

其中,address 表示指定要操作的具体行,pattern 指的是需要替换的内容,replacement 指的是要替换的新内容。

关于指定具体操作行(address)的用法,这里先不做解释,文章后续会对其做详细介绍。

此命令中常用的 flags 标记如表 2 所示。

表 2 sed s命令flags标记及功能
flags 标记 功能
n 1~512 之间的数字,表示指定要替换的字符串出现第几次时才进行替换,例如,一行中有 3 个 A,但用户只想替换第二个 A,这是就用到这个标记;
g 对数据中所有匹配到的内容进行替换,如果没有 g,则只会在第一次匹配成功时做替换操作。例如,一行数据中有 3 个 A,则只会替换第一个 A;
p 会打印与替换命令中指定的模式匹配的行。此标记通常与 -n 选项一起使用。
w file 将缓冲区中的内容写到指定的 file 文件中;
& 用正则表达式匹配的内容进行替换;
n 匹配第 n 个子串,该子串之前在 pattern 中用 () 指定。
转义(转义替换部分包含:&、 等)。

比如,可以指定 sed 用新文本替换第几处模式匹配的地方:

[root@localhost ~]# sed 's/test/trial/2' data4.txt
This is a test of the trial script.
This is the second test of the trial script.

可以看到,使用数字 2 作为标记的结果就是,sed 编辑器只替换每行中第 2 次出现的匹配模式。

如果要用新文件替换所有匹配的字符串,可以使用 g 标记:

[root@localhost ~]# sed 's/test/trial/g' data4.txt
This is a trial of the trial script.
This is the second trial of the trial script.

我们知道,-n 选项会禁止 sed 输出,但 p 标记会输出修改过的行,将二者匹配使用的效果就是只输出被替换命令修改过的行,例如:

[root@localhost ~]# cat data5.txt
This is a test line.
This is a different line.
[root@localhost ~]# sed -n 's/test/trial/p' data5.txt
This is a trial line.

w 标记会将匹配后的结果保存到指定文件中,比如:

[root@localhost ~]# sed 's/test/trial/w test.txt' data5.txt
This is a trial line.
This is a different line.
[root@localhost ~]#cat test.txt
This is a trial line.

在使用 s 脚本命令时,替换类似文件路径的字符串会比较麻烦,需要将路径中的正斜线进行转义,例如:

[root@localhost ~]# sed 's//bin/bash//bin/csh/' /etc/passwd

  sed的特殊操作:

1:反斜杠接数字是sed配合正则的分组匹配的特殊技巧名为后项引用,sed命令在使用正则匹配时会记住圆括号即分组匹配匹配到的内容,使用反斜杠接数字的方式即可取出对应顺序被sed记住的内容,需要注意的是sed最多只能记住九个分组匹配的内容,也就是说反斜杠后面能接的最大的数字是九。

&:在sed匹配中这个符号表示前面需要被替换掉的内容。

3、企业实际使用案例

1)优化SSH配置

#在ssh配置文件的13行之前插入5行配置,每一行配置用n分隔
sed -i '13i Port 52113nPermitRootLogin nonPermitEmptyPasswords nonUseDNS nonGSSAPIAuthentication no' /etc/ssh/sshd_config

2)打印文件内容但不包含oldboy

文件内容如下:

101,oldboy,CEO
102,zhangyao,CTO
103,alex,COO
104,yy,CFO
105,feixue,CIO

#将匹配有oldboy的行删除即可在输出内容中不显示包含oldboy的行,因为没加-i参数所以对#文件没有实际影响
sed  '/oldboy/d' person.txt

3)指定行修改配置文件

#修改selinux的配置文件,将selinux的级别从enforcing改为disabled
sed  -i  '7s/enforcing/disabled/'  /etc/selinux/config

4)系统开机启动项优化

chkconfig  --list|grep '3:on'|grep  -vE  'sshd|crond|network|rsyslog|sysstat'|awk  '{print $1}'|sed -r  's/^(.*)/chkconfig 1 off/g'|bash

5)批量重命名文件

/test目录下有如下文件:

stu_1029999_1_finished.jpg stu_1029999_2_finished.jpg  stu_1029999_3_finished.jpg  stu_1029999_4_finished.jpg  stu_1029999_5_finished.jpg

ls  /test/*jpg|sed -r 's/(^.*)_finished.*/mv & 1.jpg/g'|bash

About the Author

Avatar photo

今生在线

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

此站点使用Akismet来减少垃圾评论。了解我们如何处理您的评论数据