sed:逐行做文本处理
可以实现所有vi实现的功能,是编辑器也是一门语言。最常用的是替换功能,还有打印和删除等等
打印命令p:
先构造sedp.txt文件,内容如下:
[root@test test]# cat sedp.txt
aaaa this is a line
bbbb this is b line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
1.按照行号打印
格式:sed <-n> ‘1<,3>p’ file
或者使用管道传递数据 sed <-n> ‘1<,3>p’
[root@test test]# sed ‘1p’ sedp.txt (写法一)
aaaa this is a line
aaaa this is a line
bbbb this is b line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
[root@test test]# cat sedp.txt|sed ‘1p’(写法二)
aaaa this is a line
aaaa this is a line
bbbb this is b line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
默认的sed处理完一行会把原始文件再打印一次,所以第1行打印了2次。-n 参数可以关闭默认功能
[root@test test]# sed -n ‘1p’ sedp.txt (打印第1行)
aaaa this is a line
[root@test test]# sed -n ‘3p’ sedp.txt (打印第3行)
bbbb this is b line
[root@test test]# sed -n ‘1,3p’ sedp.txt (打印第1-3行)
aaaa this is a line
bbbb this is b line
2.打印匹配行(相当于egrep)
在引号中,在打印命令“p”前,可以放置一对/标识符,来代表匹配。形如‘/ /’。
[root@test test]# cat sedp.txt
aaaa this is a line
bbbb this is b line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
[root@test test]# sed -n ‘/c/p’ sedp.txt (打印含有字母c的行)
cccc this is c line
[root@test test]# sed -n ‘/^c/p’ sedp.txt (打印以字母c开头的行)
cccc this is c line
( )寄存器:类似于python中的分组,只在当前正则表达式内有效。( )中的匹配内容将被放置在临时寄存器中,之后对该寄存器的引用为\1,如果有第二对( ),引用为\2。这个在替换中经常用到
[root@test test]# sed -n ‘/([a-z])\1\1/p’ sedp.txt (含有连续出现3次字母的行)
aaaa this is a line
bbbb this is b line
cccc this is c line
dddd this is d line
[root@test test]# sed -n ‘/([a-z])\1\1\1*/p’ sedp.txt(含有连续出现3次以上字母的行)
aaaa this is a line
bbbb this is b line
cccc this is c line
dddd this is d line
[root@test test]# sed -n ‘/aaaa/,/cccc/p’ sedp.txt (打印aaaa和cccc之间的行)
aaaa this is a line
bbbb this is b line
cccc this is c line
[root@test test]# sed -n ‘/a/,/c/p’ sedp.txt
aaaa this is a line
bbbb this is b line
cccc this is c line
删除命令d:
在默认情况下,sed的删除操作并不直接作用于文件本身,而仅仅是在打印的时候不打印匹配的行,有些类似于grep –v。如果需要删除操作作用于文件,在有文件写权限的前提下,可以使用sed –i参数来使删除操作作用于文件。注意:不是所有的unix自带的sed工具都有这个功能。
删除指定的行:-i参数真正的删除文件,但是一般不这么使用
[root@test test]# cat sedd.txt
aaaa this is a line
bbbb this is b line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
[root@test test]# sed ‘3d’ sedd.txt (删除第3行,只是不显示第3行)
aaaa this is a line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
[root@test test]# cat sedd.txt
aaaa this is a line
bbbb this is b line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
[root@test test]# sed -i ‘3d’ sedd.txt (真正的从文件中删除第3行)
[root@test test]# cat sedd.txt
aaaa this is a line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
[root@test test]#
删除匹配的行,删除以this开头的行
[root@test test]# cat sedd.txt
aaaa this is a line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
this is a line,too
thisis b line
[root@test test]# sed ‘/^<this>/d’ sedd.txt
aaaa this is a line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
thisis b line
[root@test test]# sed ‘/^this /d’ sedd.txt
aaaa this is a line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
thisis b line
[root@test test]#
删除连续a和连续d之间的行
[root@test test]# cat sedd.txt
aaaa this is a line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
this is a line,too
thisis b line
[root@test test]# sed ‘/aaa*/,/ddd*/d’ sedd.txt
e this is e line
f this is f line
this is a line,too
thisis b line
替换命令s:
- Sed替换的基本格式
sed ‘s/待替换的内容/新的内容 /’
s:表示替换,放到开头
待替换的内容:可以是字符串,也可以是正则表达式
新的内容:不能是正则表达式,但是可以是待替换的内容的寄存器
2. 全局替换:/g
如上例所示含有字母i的一行,并没有把所有的字母i都替换掉。这是因为sed默认替换第一个匹配的项,替换一次后结束该行。如果要把一行内所有的匹配项都替换,需要加全局命令“g”。
3. 指定行替换
无论是“p”或者是“d”都出现在指定的行号后面或者匹配的后面。实际上替换的“s”也是这样的,只不过默认的是对文件全篇进行替换,而不是指定行或者匹配行替换。
4. 匹配行替换
将“a example”替换为“an example”。注意考虑全局属性和a的限制
[root@test test]# cat seds.txt
aaaa this is a line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
this is a example,too
this is a example for seds. this is a banana
[root@test test]# sed ‘/example/s/a/an/’ seds.txt (第1个匹配的a被替换为an)
aaaa this is a line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
this is an example,too
this is an example for seds. this is a banana
[root@test test]# sed ‘/example/s/a/an/g’ seds.txt (所有的a都被替换为an)
aaaa this is a line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
this is an exanmple,too
this is an exanmple for seds. this is an bannannan
[root@test test]# sed ‘/example/s/a( *example)/an\1/g’ seds.txt (只有example前的a原样替换为an)
aaaa this is a line
cccc this is c line
dddd this is d line
e this is e line
f this is f line
this is an example,too
this is an example for seds. this is a banana
- 删除某些字符
[root@test test]# echo “/path/to/home”|sed ‘s/p//’(删除p)
/ath/to/home
[root@test test]# echo “/path/to/home”|sed “s/^/[a-z][a-z]*//” (删掉一级目录)
/to/home
//利用正则的贪婪性s/ ^/…*/ / / /
[root@test test]# echo “/path/to/home”|sed “s/^/…*”(保留最后一级目录)
/home
很多//放到一起的话可读性太差,sed支持3个成对出现的字符(有一些除外)
[root@test test]# echo “/path/to/home”|sed “s@^/…*/@/@”
/home
[root@test test]# echo “/path/to/home”|sed “soxxxx^”
/path/txxxx/home
[root@test test]# echo “/path/to/home”|sed “sbobxxxxb”(待匹配的字符中没有出现的字节都可以)
/path/txxxx/home
6.常用例子
行首加上#
删除行尾的.
将连续字母变成一个,并且只显示修改行
[root@test test]# cat seds.txt
aaaa this is a line.
cccc this is c line.
dddd this is d line.
e this is e line.
f this is f line.
this is a example,too.
this is a example for seds. this is a banana.
[root@test test]# cat seds.txt |sed ‘s/([a-z])\1\1*/\1/g’
a this is a line.
c this is c line.
d this is d line.
e this is e line.
f this is f line.
this is a example,to.
this is a example for seds. this is a banana.
[root@test test]# cat seds.txt |sed -n ‘s/([a-z])\1\1*/\1/gp’
a this is a line.
c this is c line.
d this is d line.
this is a example,to.
当匹配对象中含有”/”
一般是需要处理目录路径的时候。比如,将”/etc”换成”/usr/local/etc”。
两种方法:
方法一:通过转义符,这种方法令人费解。
方法二:将s/ / /换成任意字符分割,比如s# # #: