文章目录
- 8.1 介绍
- 8.1.1 工作流程
- 8.1.2 命令格式
- 8.2 sed 使用
- 8.2.1 查找/打印
- 8.2.2 添加
- 8.2.3 修改
- 8.2.4 删除
- 8.3 保存操作后的内容
8.1 介绍
sed编辑器被称作流编辑器( stream editor),和普通的交互式文本编辑器恰好相反。在交互式文本编辑器中(比如vim),你可以用键盘命令来交互式地插入、删除或替换数据中的文本。流编辑器则会在编辑器处理数据之前基于预先提供的一组规则来编辑数据流。
它是文本处理中非常有用的工具,能够完美的配合正则表达式使用,处理时,把当前处理的行存储在临时缓冲区中,称为模式空间,接着用sed命令处理缓冲区中的内容,处理完成后,把缓冲区的内容送往屏幕。接着处理下一行,这样不断重复,直到文件末尾。文件内容并没有改变。
8.1.1 工作流程
sed编辑器可以根据命令来处理数据流中的数据,这些命令要么从命令行中输入,要么存储在一个命令文本文件中。 sed编辑器会执行下列操作。
(1) 一次从输入中读取一行数据。
(2) 根据所提供的编辑器命令匹配数据。
(3) 按照命令修改流中的数据。
(4) 将新的数据输出到STDOUT。
8.1.2 命令格式
sed [选项] [sed内置命令字符] [输入文件]
选项;
-n 取消默认sed的输出,常与sed内置命令p一起用
-i 直接将修改结果写入文件,不用-i,sed修改的是内存数据
-e 多次编辑,不需要管道符
-r 支持正则扩展
sed的内置命令用于对文件进行不同的操作功能,如对文件增删改查。
sed常用内置命令字符:
a append,对文本追加,在指定行后面添加一行/多行文本
d Delete,删除匹配行
i insert,表示插入文本,在指定行前添加一行/多行文本
p print,打印匹配行的内容,通常与-n一起用
s/正则/替换内容/g 匹配正则内容,然后替换内容(支持正则),结尾g表示全局匹配
sed匹配范围:
范围 | 解释 |
---|---|
空地址 | 全文处理,即每行都处理 |
单地址 | 指定文件某一行 |
/pattern/ | 被模式匹配到的每一行 |
范围区间 | 10,20 十到二十行 ,10,+5 第10行向下5行 ,/parttern1/,/pattern2/ |
步长 | 1~2 表示1、3、5、7、9奇数行,2~2 表示2、4、6、8、10偶数行 |
使用示例:替换字符串
# 输出指定字符串到屏幕上
[root@openEuler ~]# echo "This is a test"
This is a test
# 将字符串中的 is 替换为 IS 后再输出到屏幕上
[root@openEuler ~]# echo "This is a test" | sed "s/is/IS/"
ThIS is a test
# 将字符串中所有的 is 替换为 IS 后再输出到屏幕上
[root@openEuler ~]# echo "This is a test" | sed "s/is/IS/g"
ThIS IS a test
下面我们编写一个文件,然后来演示 sed 命令的各种用法:
[root@openEuler ~]# vim test.txt
[root@openEuler ~]# cat test.txt
I have a pen
I have an apple
I have a book
I love you
8.2 sed 使用
8.2.1 查找/打印
查找格式,p 表示显示,一般和 -n 一起使用
格式 | 说明 |
---|---|
‘1p’ | 指定行号进行查找 |
‘1,5p’ | 指定行号范围进行查找 |
‘//p’ | 类似于grep的过滤,//里面可以写正则 |
‘/10:00/,/11:00/p’ | 表示范围的过滤 |
‘1,/haha/p’ | 混合,从1到包含有haha行结束,了解 |
例1:接合 -n 选项来输出第三行内容
[root@openEuler ~]# sed '1p' test.txt
I have a pen
I have a pen
I have an apple
I have a book
I love you
[root@openEuler ~]# sed '3p' test.txt
I have a pen
I have an apple
I have a book
I have a book
I love you
[root@openEuler ~]# sed -n '3p' test.txt
I have a book
例2:输出 test.txt 文件中1到3行内容
[root@openEuler ~]# sed -n '1,3p' test.txt
I have a pen
I have an apple
I have a book
例3:在 test.txt 文件中查找 hive
# 查找内容中包含有 hive 的行
[root@openEuler ~]# sed -n '/hive/p' test.txt
I have a pen
I have an apple
I have a book
# 查找内容中包含有 love 的行
[root@openEuler ~]# sed -n '/love/p' test.txt
I love you
例4:在 test.txt 文件中查找 pen 到 book 的行
[root@openEuler ~]# sed -n '/pen/,/boo/p' test.txt
I have a pen
I have an apple
I have a book
例5,在 test.txt 文件中从第一行开始查找,直到包含 apple 字符串为止
[root@openEuler ~]# sed -n '1,/apple/p' test.txt
I have a pen
I have an apple
8.2.2 添加
在 sed 中增加数据的格式如下:
命令 | 说明 |
---|---|
c | replace,表示替换 |
a | append 表示追加 |
i | insert 表示插入 |
示例:
[root@openEuler ~]# vim test.txt
[root@openEuler ~]# cat test.txt
I have a pen
I have an apple
I have a book
I love you
# 打印,第3行
[root@openEuler ~]# sed -n '3p' test.txt
I have a book
# 在每一行后添加新的内容
[root@openEuler ~]# sed 'ahallo world' test.txt
I have a pen
hallo world
I have an apple
hallo world
I have a book
hallo world
I love you
hallo world
# 在test.txt文件的第2行之后添加 hello
[root@openEuler ~]# sed '2ahello' test.txt
I have a pen
I have an apple
hello
I have a book
I love you
# 在第一行之前加hello
[root@openEuler ~]# sed 'ihello' test.txt
hello
I have a pen
hello
I have an apple
hello
I have a book
hello
I love you
[root@openEuler ~]# sed 'i\hello' test.txt
hello
I have a pen
hello
I have an apple
hello
I have a book
hello
I love you
# 在test.txt文件中第4行前面加上内容
[root@openEuler ~]# sed '4i\shell sed' test.txt
I have a pen
I have an apple
I have a book
shell sed
I love you
8.2.3 修改
在修改文件内容时,我们可以使用以下的替换格式:
1. s#被替换的内容#替换后的内容#g
2. s/被替换的内容/替换后的内容/g
3. s@被替换的内容@替换后的内容@g
在上面的格式中,g 表示全局替换。
s 表示 substriute
使用示例:
# 1. 将test.txt文件中的 have 替换为 Have
[root@openEuler ~]# sed 's#have#Have#g' test.txt
I Have a pen
I Have an apple
I Have a book
I love you
[root@openEuler ~]# sed 's/have/Have/g' test.txt
I Have a pen
I Have an apple
I Have a book
I love you
[root@openEuler ~]# sed 's%have%Have%' test.txt
I Have a pen
I Have an apple
I Have a book
I love you
# 2. 将输入的 123456 变为 <123456> 输出
[root@openEuler ~]# echo 123456
123456
[root@openEuler ~]# echo 123456 | sed 's/(.*)/<1>/g'
123456
[root@openEuler ~]# echo 123456 | sed -r 's/(.*)/<1>/g'
<1>
[root@openEuler ~]# echo 123456 | sed -r 's/(.*)/<\1>/g'
<123456>
# 3. ip a 通过反向引用取出 ens160 网卡的ip
# 3.1. 查看ens160设备的网卡信息的命令
[root@openEuler ~]# ip a s ens160
[root@openEuler ~]# ip a show ens160
[root@openEuler ~]# ifconfig ens160
例如:
[root@openEuler ~]# ip a show ens160
2: ens160: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state UP group default qlen 1000
link/ether 00:0c:29:24:80:97 brd ff:ff:ff:ff:ff:ff
inet 192.168.72.131/24 brd 192.168.72.255 scope global noprefixroute ens160
valid_lft forever preferred_lft forever
inet6 fe80::20c:29ff:fe24:8097/64 scope link noprefixroute
valid_lft forever preferred_lft forever
# 3.2 我们可以取出上面结果中第3行的内容
[root@openEuler ~]# ip a show ens160|sed -n '3p'
inet 192.168.72.131/24 brd 192.168.72.255 scope global noprefixroute ens160
[root@openEuler ~]# ip a show ens160|sed -n '3p'|sed -r 's#(^.*t )(.*)(/.*$)#\2#g'
192.168.72.131
#或者
[root@openEuler ~]# ip a show ens160|sed -n '3p'|sed -r 's/(^.*t )(.*)(\/.*$)/\2/g'
192.168.72.131
以上正则表达式说明:
- (^.*t ):表示获取 " inet " 的内容
- (.*):表示获取IP地址 192.168.72.131
- (/.*$):表示获取 /后的所有内容,即 /24 brd 192.168.72.255 scope global noprefixroute ens160
- \2:表示获取第2组内容
示例4. stat /etc/hosts 取出权限 644
[root@openEuler ~]# stat /etc/hosts|sed -n '4p'|sed -r 's/^.*\(0(.*)(\/-.*$)/\1/g'
644
8.2.4 删除
在 sed 中删除内容是使用 d 命令来实现的,它的格式为:
格式 | 说明 |
---|---|
‘1d’ | 指定等号进行删除 |
‘1,5d’ | 范围删除,删除1到5行 |
‘//d’ | 使用正则表达式来进行匹配删除 |
‘/10:00/,/11:00/d’ | 表示范围删除 |
‘1,/haha/d’ | 混合模式,从1到包含haha的行结束 |
示例:
1. 删除test.txt文件的第3行
# 1.1 原来的内容
[root@openEuler ~]# cat test.txt
I have a pen
I have an apple
I have a book
I love you
## 1.2 删除后的内容
[root@openEuler ~]# sed '3d' test.txt
I have a pen
I have an apple
I love you
2. 删除test.txt文件中从第2行开到哪第第4行
[root@openEuler ~]# sed '2,4d' test.txt
I have a pen
3. 删除test.txt文件的第1行到包含有book的行
[root@openEuler ~]# sed '1,/book/d' test.txt
I love you
[root@openEuler ~]# sed '1,/apple/d' test.txt
I have a book
I love you
4. 删除/etc/ssh/sshd_config文件的空行和带#号行以外的所有行
# 4.1 获取空行和带#号的行
[root@openEuler ~]# grep -E '^$|#' sshd_config
[root@openEuler ~]# sed -n -r '/^$|#/p' sshd_config
# 4.2 删除空行和带#号的行
[root@openEuler ~]# sed -r '/^$|#/d' sshd_config
# 4.3 删除空行和带#号和行以外的
[root@openEuler ~]# sed -r '/^$|#/!d' sshd_config
8.3 保存操作后的内容
在 10.2 节中使用的 sed 命令所有操作都是在内存中完成了,它并不会影响原来的文件内容。如果希望操作后改变原来文件的内容,我们就需要使用 sed 命令的 -i 选项。
1. 在test.txt文件的第3行位置添加ni hao wo hao da jia hao,并写入到文件中
[root@openEuler ~]# sed -i '3a\ni hao wo hao da jia hao' test.txt
[root@openEuler ~]# cat test.txt
I have a pen
I have an apple
I have a book
ni hao wo hao da jia hao
I love you