目录:
(一)sed基本语法
(二)sed实战演练


(一)sed基本语法
(1.1)sed是一项Linux系统命令,功能通awk类似,差别在于sed简单,对列处理的功能要差一些,awk的功能复杂,对列处理的功能比较强大。sed的全称是:Stream EDitor
(1.2)sed属于行编辑器,sed作为文本编辑器只是用来处理纯ASCII码的文本的,在操作文本的时候是逐行操作的,并不能一次性操作多行。sed作为文本编辑器并不处理文本文件本身,每当处理一个文件的时候,它会逐行读取文件,每次将一行读取到内存空间中,然后在内存中完成编辑,然后将内存中编辑好的结果输出到屏幕上,这个内存空间我们称之为“模式空间”。sed并不是每一行都处理,它会按照某种指定的模式进行过滤,即符合条件的我们就处理,不符合模式条件的就不处理。sed把符合条件的行读进模式空间进行匹配,如果匹配到了就会在模式空间中使用后面的编辑命令对其完成编辑,并将完成编辑的结果输出到屏幕上来。
(1.3)默认情况下,sed不编辑原文件,仅对模式空间中的数据做处理。其中sed命令的语法总结为:“sed 'AddressCommand' file1 file2”
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第1张图片
(1.4)首先对于sed命令中的Address部分,我们可以用以下的几种方式来表示,第一种是“StartLine,EndLine”,比如“1,100”表示从第1行到第100行,其中$符号表示最后一行;第二种我们可以使用正则表达式“/RegExp/”,例如我们可以使用“/^root/”表示以root字符串开头的行;第三种我们可以使用“/pattern1/,/pattern2/”表示第一次被pattern1匹配到的行开始至第一次被pattern2匹配到的行结束;第四种可以以LineNumber表示指定的行;第五种方法我们可以使用“StartLine,+N”表示的是从startLine开始,向后的N行。
(1.5)参数d
(1.5.1)对于Command部分,首先第一个参数为“d”,表示的是删除符合条件的行,例如我们以/etc/fstab文件为例,使用“1,4d”删除第1至第4行(图1-2)。如果我们希望删除第5行到最后1行的内容,则可以使用'5,$d'进行表示(图1-3)。
# sed '1,4d' /etc/fstab---将/etc/fstab文件中的第1至第4行删除
# sed '5,$d' /etc/fstab---将/etc/fstab文件中的第5行到最后一行删除
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第2张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第3张图片
(1.5.2)如果我们指定删除文件中字符串包含“oot”的所有行,我们在vms002主机上将/etc/fstab文件拷贝到root用户的家目录下命名为fstab文件,并且编辑如下的文件内容(图1-4)。然后我们使用“# sed '/oot/d' fstab”命令进行文本过滤,此时我们发现过滤出来的内容中已经没有了cat fstab中标红的两行了(图1-5)。
# sed '/oot/d' fstab---删除文件中字符串包含“oot”的所有行
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第4张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第5张图片
(1.5.3)如果我们希望删除当前行到当前行的后2行内容,则可以使用“1,+2d”的参数表示,此时我们发现显示的内容中第1行到第3行已经过滤掉了(图1-6),如果我们需要删除需要删除某一指定的行,则可以直接数字加上字母d即可。
# sed '1,+2d' fstab---删除第1行到第3行的内容
# sed '1d' fstab---删除第1行的内容
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第6张图片
(1.6)对于Command部分,接着第二个参数是“p”,表示的是显示符合条件的行。比如现在我们需求是显示以“/”斜线开头的行,此时我们需要在sed命令后跟一个“-n”的参数,即“sed -n”表示静默模式,不再默认显示模式空间中的内容。而“^/”表示的是以斜线开头的行,不过需要用“\”进行转义,根据Address的第二种情况,我们需要以“/RegExp/”进行过滤,所以最后的格式为“/^\//p”
# sed -n '/^\//p' fstab---查询并显示以“/”斜线开头的行
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第7张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第8张图片
(1.7)对于Command部分,接着第三个参数是“a \string”,表示的是在指定的行后面追加新行,内容为string。此时我们发现以“^/”开头的行的下一行都添加了一个新行“# hello world”(图1-9),如果我们希望能够添加两行,则可以使用“\n”作为分隔符(图1-10)。
# sed '/^\//a # hello world' fstab---在以“^/”开头的行的末尾追加新行,追加的内容为“# hello world”
# sed '/^\//a # hello world\n# hello Linux' fstab---在以“^/”开头的行的末尾添加两行,且以“\n”作为分隔符
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第9张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第10张图片
(1.8)对于Command部分,接着第四个参数是“i \string”,表示的是在指定的行前面添加新行,内容为string。
# sed '/^\//i # hello world' fstab---在以“^/”开头的行的上一行插入新行,追加的内容为“# hello world”
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第11张图片
(1.9)对于Command部分,接着第五个参数是“r FILE”,表示的是将指定的文件内容添加至符合条件的行处。我们要求在fstab文件中,从第2行开始,将/etc/issue文件添加进来,此时便可以使用“2r /etc/issue”参数(图1-12);如果我们希望将/etc/issue文件添加到最后一行的后面,则可以使用“$r /etc/issue”参数表示(图1-13);如果我们希望在指定的行,例如1至3行后面添加etc/issue文件,则可以使用“1,3r /etc/issue”参数(图1-14)。
# sed '2r /etc/issue' fstab---从第2行开始,将/etc/issue文件添加进来
# sed '$r /etc/issue' fstab---将/etc/issue文件添加到最后一行的后面
# sed '1,3r /etc/issue' fstab---设置从第1至第3行,每一行后面都添加/etc/issue文件
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第12张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第13张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第14张图片
(1.10)对于Command部分,接着第六个参数是“w FILE”,表示将指定范围内的内容另存至指定的文件中。例如我们的需求是将fstab文件中有“oot”的行,提取出来保存至/tmp/oot.txt文件中,我们使用“/oot/w /tmp/oot.txt”参数表示,此时我们发现在/tmp/oot.txt文件中存储的是fstab文件中含有oot的行。
# sed -n '/oot/w /tmp/oot.txt' fstab---将fstab文件中有“oot”的行,提取出来保存至/tmp/oot.txt文件中
# cat oot.txt---在/tmp目录下查看oot.txt文件
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第15张图片
(1.11)查找并替换
(1.11.1)对于Command部分,接着第七个参数是“s/pattern/string/”,表示的是查找并替换,默认只替换每行中第一次被模式匹配到的字符串。其中pattern处表示的可以是字符串也可以是正则表达式,而string处则只可以使用字符串。我们希望将fstab文件中含有oot的字符串替换为OOT大写的字符串,此时可以使用“s/oot/OOT/”参数。
# sed 's/oot/OOT/' fstab---将fstab文件中含有oot的字符串替换为OOT大写的字符串
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第16张图片
(1.11.2)如果我们希望将fstab文件中以“/”开头的行,将斜线替换为“#”号,则可以使用使用“s/^\//#/”参数,此时我们发现在开头两行的“/”斜线已经被替换为“#”号了。
# sed 's/^\//#/' fstab---将fstab文件中以“/”开头的行,将斜线替换为“#”号br/>![](https://s1.51cto.com/images/blog/201912/25/8447fbe61112b5852f7bce21d8aa5187.png?x-oss-process=image/watermark,size_16,text_QDUxQ1RP5Y2a5a6i,color_FFFFFF,t_100,g_se,x_10,y_10,shadow_90,type_ZmFuZ3poZW5naGVpdGk=)
(1.11.3)如果我们想要将fstab文件中的所有“/”斜线都替换为“#”号,此时我们应该使用全局替换符g,此时我们发现系统中所有的斜线都被替换为了“#”号(图1-18)。如果我们在查找替换的时候不想用“/”斜线作为分隔符,也是可以使用其他特殊字符作为分隔符的,例如“#”或者“@”等(图1-19)。
g:全局替换
i:忽略字符大小写
# sed 's/\//#/g' fstab---将fstab文件中的所有“/”斜线都替换为“#”号
# sed 's@/@#@g' fstab---使用“@”作为分隔符,并将fstab文件中的所有“/”斜线都替换为“#”号
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第17张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第18张图片
(1.12)替换表达式类型字符
(1.12.1)对于Command部分,接着第八个参数是“l..e”,例如将like转换为liker,将love转换为lover,此时我们使用“&”符号,代表引用表达式部分的内容,然后在再加字母“r”表示替换为我们所希望的格式。
# sed 's#l..e#&r#g' sed.txt---使用“&”符号,代表引用表达式部分的内容,然后在再加字母“r”表示替换为我们所希望的格式
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第19张图片
(1.12.2)如果我们希望使用后项引用的方式来进行字符替换,则可以使用如下的方式操作。我们将like替换为liker,我们将love替换为lover,使用后项引用的方式“s#(l..e)#\1r#g”参数来替换字符(图1-21);如果我们希望将like替换为Like,将love替换为Lover,则此时我们只有使用后项引用的方式使用参数“s#l(..e)#L\1#g”,才可以符合要求(图1-22)。
# sed 's#(l..e)#\1r#g' sed.txt---将like替换为liker,我们将love替换为lover
# sed 's#l(..e)#L\1#g' sed.txt---将like替换为Like,将love替换为Lover
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第20张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第21张图片
(1.13)如果我们希望修改原文件时,此时使用“sed -i”选项即可,直接修改原文件。如果我们使用“sed -e”参数时,表示可以同时执行多个脚本。当然我们也可以将多个脚本放在一个原文件中,然后使用“sed -f”可以指定读取这个原文件。最后我们还可以使用“sed -r”参数,表示使用扩展正则表达式。
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第22张图片


(二)sed实战演练
(2.1)示例:现在我们的需求是将执行的history命令的行首的空白行清除掉,并且能够获取到history命令的第一列的所有信息,此时我们可以使用“^[[:space:]]*”表示行首为任意空格,然后再使用cut命令将打印结果的第一列显示出来(图1-25)。
# history | sed 's#^[[:space:]]*##g' | cut -d' ' -f1---执行的history命令的行首的空白行清除掉,并且能够获取到history命令的第一列的所有信息
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第23张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第24张图片
(2.2)示例:删除/boot/grub2/grub.cfg文件中行首的空白符。
# sed -r 's@^[[:space:]]+@@g' /boot/grub2/grub.cfg---将/boot/grub2/grub.cfg文件中的行首的空白字符去除顶格显示
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第25张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第26张图片
(2.3)示例:替换/etc/inittab文件中“id:3:initdefault:”一行中的数字为5。我们将/etc/inittab文件拷贝到当前目录,然后在最后一行添加一行“id:3:initdefault:”(图2-4),此时我们使用sed可以得到所需的结果。
# sed 's@(id:)[0-9](:initdefault:)@\15\2@g' inittab---将inittab文件中的最后一行“id:3:initdefault:”修改为“id:5:initdefault:”
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第27张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第28张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第29张图片
(2.4)示例:删除/etc/inittab文件中的空白行。
# cat /etc/inittab
# sed '/^$/d' /etc/inittab
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第30张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第31张图片
(2.5)示例:删除/etc/inittab文件中开头的#号。
# sed 's@^#@@g' inittab
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第32张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第33张图片
(2.6)示例:删除某文件中开头的#号及后面的空白字符,但要求#号后面必须有空白字符,#号后没有空白字符的该#号不删除。
# sed -r 's@^#[[:space:]]+@@g' /etc/inittab
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第34张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第35张图片
(2.7)示例:先找出某文件中以空白字符开头并且后面跟#号的行,然后删除该行中的开头的空白字符及#号。
# sed -r 's@^[[:space:]]+#@@g' /etc/inittab
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第36张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第37张图片
(2.8)示例:取出一个文件或目录路径的父目录名称。首先我们可能遇到的文件或目录如下:“/etc/rc.d”、“/etc/rc.d/”、“/etc/rc.d/abc”、“/etc/rc.d/abc/”,然后取出文件或者目录的父目录并显示出来。
# echo "/etc/rc.d/" | sed -r 's@^(/.*/)[^/]+/?@\1@g'---获取目录的父目录
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第38张图片
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第39张图片
(2.9)示例:取出一个文件或目录路径的基名。首先我们可能遇到的文件或目录如下:“/etc/rc.d”、“/etc/rc.d/”、“/etc/rc.d/abc”、“/etc/rc.d/abc/”,然后取出文件或者目录的基名例如rc.d或者abc显示出来。
# echo "/etc/rc.d" | sed -r 's@^/.*/([^/]+)/?@\1@g'---显示/etc/rc.d的基名
【讲清楚,说明白!】Linux从业人员必备工具--sed文本处理神器_第40张图片

—————— 本文至此结束,感谢阅读 ——————