shell之sed的学习总结
sed 工具简介可以进行取代、删除、新增、撷取特定行等等的功能呢!
#sed [-nefr]
参数:
-n:使用安静(silent)模式。在一般sed 的用法中,所有来自STDIN
的数据一般都会被列出到屏幕上。但如果加上-n 参数后,则只有经过
sed特殊处理的那一行(或者动作)才会被列出来。
-e:直接在指令列模式上进行sed 的动作编辑;
-f:直接将sed 的动作写在一个档案内,-f filename 则可以执行filename 内的sed动作;
-r:sed 的动作支持的是延伸型正则表达式的语法。(预设是基础正则表达式语法)
-i:直接修改读取的档案内容,而不是由屏幕输出。
动作说明: ]function
n1, n2 :不见得会存在,一般代表『选择进行动作的行数』,举例来说,如果我的动作是需要在10 到20 行之间进行的,则『10,20[动作行为] 』
function 有底下这些:
a :新增,a 的后面可以接字符串,而这些字符串会在新的一行出现(目前的下一行)~
c :取代,c 的后面可以接字符串,这些字符串可以取代n1,n2 之间的行!
d :删除,因为是删除啊,所以d 后面通常不接任何咚咚;
i :插入,i 的后面可以接字符串,而这些字符串会在新的一行出现(目前的上一行);
p :打印,亦即将某个选择的数据印出。通常p 会与参数sed -n 一起运作~
s :取代,可以直接进行取代的工作哩!通常这个s 的动作可以搭配正则表达式!例如1,20s/old/new/g 就是啦!
r : 从一个文件读入
w:把行写入一个文件
g :在一行上进行全局替换
! :把命令应用到除了选出的行以外的其他所有的行
n :读下一输入行,并开始用下一个命令处理换行符,而不是用第一个命令
h :把模式空间内容复制到一个固定缓存
H : 把模式空间内容添加到一个固定缓存
g : 得到固定缓存里所有的禀复制到模式缓存,重写其内容
G : 得到固定缓存的内容并复制到模式缓存,添加到里面
x : 用模式空间的内容交换固定缓存的内容
y : 把一个字符转换成另一个(不能和整则表达式元字符一起使用)
另外我们还有提一个逗号,如第一行到第6行可以用1,6 如果想找aa到dd之间的内容可以用/aa/,/dd/就可以。此说一下用法,一边后面看出他的意思。
sed的元字符集:
^
锚定行的开始 如:/^sed/匹配所有以sed开头的行。
$
锚定行的结束 如:/sed$/匹配所有以sed结尾的行。
.
匹配一个非换行符的字符 如:/s.d/匹配s后接一个任意字符,然后是d。
*
匹配零或多个字符 如:/*sed/匹配所有模板是一个或多个空格后紧跟sed的行。
[]
匹配一个指定范围内的字符,如/ed/匹配sed和Sed。
[^]
匹配一个不在指定范围内的字符,如:/[^A-RT-Z]ed/匹配不包含A-R和T-Z的一个字母开头,紧跟ed的行。
\(..\)
保存匹配的字符,如s/\(love\)able/\1rs,loveable被替换成lovers。
&
保存搜索字符用来替换其他字符,如s/love/**&**/,love这成**love**。
\<
锚定单词的开始,如:/\
锚定单词的结束,如/love\>/匹配包含以love结尾的单词的行。
x\{m\}
重复字符x,m次,如:/0\{5\}/匹配包含5个o的行。
x\{m,\}
重复字符x,至少m次,如:/o\{5,\}/匹配至少有5个o的行。
x\{m,n\}
重复字符x,至少m次,不多于n次,如:/o\{5,10\}/匹配5--10个o的行。
注:sed不会更改更改原 文件的内容。它的工作方式是读取文件的内容,经流编辑之后,将结果输出到标准输出。因此,要想保存sed的处理结果,用-i编辑或者w输出到一个文件。
事例:
我们用的事例用的文件是./passwd里的内容
我们先看一下前四行的内容:
# sed -n '1,4p' ./passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
删除:d
1.删除第二行,其他的显示出来
# sed '2d' passwd
root:x:0:0:root:/root:/bin/bash
daemon:x:2:2:daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
2.删除第2行到第4行的内容,其他的显示出来
# sed '2,4d' passwd
root:x:0:0:root:/root:/bin/bash
3.把含有daemon的行删除,其他的显示出来:
# sed '/daemon/d' passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
4.把不含有nologin的行删除
# sed '/nologin/!d' passwd
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
注:因为root不含有nologin所以删除了,注意!的用法。
5.把含有空格的删除,当然上面的文本不含有空格,所以下面的用法只是所以用法
sed '/^$/d' passwd
6.删除含有3个数字的行
我们先把文本改一下,增加几个数字
# cat passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:456daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
我们把有连续有3个数字的行删除
# sed '/\{3\}/d' passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
这样daemon那一行就删除了。
注:\{n\}的用法就是重复几次如:
\{3\} 正好重复3次
\{3,\} 至少3次
\{3,6\} 重复3次到6次之间
打印:p n
1.默认打印所有行,匹配的行重复打印
# sed '/root/p' passwd
root:x:0:0:root:/root:/bin/bash
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:456daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
看到上面的root行重复打印一下
2.和-n一起使用,禁止默认打印,只打印匹配行
# sed -n '/^root/p' passwd
root:x:0:0:root:/root:/bin/bash
替换:s
1.替换root为fantefei
# sed -n 's/root/fantefei/p' passwd
fantefei:x:0:0:root:/root:/bin/bash
我们看到只是替换了第一个root为fantefei,而后面的没有替换,要是全局替换要添加g
# sed -n 's/root/fantefei/gp' passwd
fantefei:x:0:0:fantefei:/fantefei:/bin/bash
这样就全替换过来了
2.删除每行开头的前两个字母
# sed 's/^..//g' passwd
ot:x:0:0:root:/root:/bin/bash
n:x:1:1:bin:/bin:/sbin/nologin
emon:x:2:2:456daemon:/sbin:/sbin/nologin
m:x:3:4:adm:/var/adm:/sbin/nologin
s/^..//g中^是开头..代表两个字符
3.删除每行末的两个字母
# sed 's/..$//g' passwd
root:x:0:0:root:/root:/bin/ba
bin:x:1:1:bin:/bin:/sbin/nolog
daemon:x:2:2:456daemon:/sbin:/sbin/nolog
adm:x:3:4:adm:/var/adm:/sbin/nolog
注意要加g啊,要不至替换第一行
4.把第2行到第4行的nologin全换成bash
# sed '2,4s/nologin/bash/g' passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/bash
daemon:x:2:2:456daemon:/sbin:/sbin/bash
adm:x:3:4:adm:/var/adm:/sbin/bash
5.把字符root到daemon之间的nologin全部换成bash
# sed '/root/,/daemon/s/nologin/bash/g' passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/bash
daemon:x:2:2:456daemon:/sbin:/sbin/bash
adm:x:3:4:adm:/var/adm:/sbin/nologin
我们看到最后一行的没有替换,这就是/root/,/daemon/的效果
6.把开头root中的ot变成fantefei
# sed 's/^\(ro\)ot/\1fantefei/' passwd
rofantefei:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:456daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
注:s/^\(ro\)ot/\1fantefei/中\(ro\)被保留为\1使用。这就是\(\)的用法
7.在有3个连续数字的后添加.5
# sed 's/\{3\}/&.5/' passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:456.5daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
看到456已经变为456.5了
这里是&的用法,保留匹配行
8.把匹配daemon的行中的nologin变为aa
# sed '/daemon/s/nologin/aa/' passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:456daemon:/sbin:/sbin/aa
adm:x:3:4:adm:/var/adm:/sbin/nologin
9.s后面不一定一定要/作为分隔符,可以用相同的两个符号作为分割符,因为有时候可以去改变/开头的文字如下面,这样就可能引起错误:
我们把root行的/bin/替换为aa
# sed '/^root/s#/bin/#aa#' passwd
root:x:0:0:root:/root:aabash
这里我们用了#作为分隔符,有效的避免了和/bin/中的/冲突
10.多次编辑用-e选项
我们把1到3行删除,然后替换其他的nologin为bash
# sed -e '1,3d' -e's/nologin/bash/' passwd
adm:x:3:4:adm:/var/adm:/sbin/bash
从文件读取:r
r命令从文本读取内容,然后输出到匹配的行后面,如果不只一个匹配行那将在每个匹配行后面输出内容
1.我们有个a的文件,里面的内容为
# cat a
loveable
我们要在root的行后输出a的文本内容
# sed '/root/r a' passwd
root:x:0:0:root:/root:/bin/bash
loveable
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:456daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
如果我们要在nologin后面输出呢,看一下:
# sed '/nologin/r a' passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
loveable
daemon:x:2:2:456daemon:/sbin:/sbin/nologin
loveable
adm:x:3:4:adm:/var/adm:/sbin/nologin
loveable
这样每个匹配的nologin都有a的内容了
写入文件内容:w
w把匹配的行写入到b的文件
# sed '/root/w b' passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:456daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
# cat b
root:x:0:0:root:/root:/bin/bash
#
添加命令:a i
1.在root后添加一行------>fantefeifantefeifantefeifantefeifantefeifantefeifantefei
页:
[1]