sed 文件流编辑器
概要: sed(stream editor)是Linux三剑客之一,常用于自动化程序的文本处理工作。
创建时间: 2022.12.18 21:39:04
更新时间: 2023.07.28 23:08:40
sed工作原理
不同于大名鼎鼎的vim,sed是一种流编辑器,它使用预先设定好的编辑命令对输入的文本进行编辑,完成后输出编辑结果。
工作原理
- 从输入文件中读取内容,每次只读取一行文件,并将其存储到临时的缓存区,即
模式空间
中
- 使用输入的sed命令处理此行文本
- 处理完毕此行文本后,将缓存区中内容输出到屏幕
- 继续处理下一行,直到文件结束
提示
在不使用重定向输入工具的情况下,sed不会更改原始文件(除非使用-i
参数)
正则表达式
参考三剑客之一grep
工具:在grep工具中,使用正则表达式 | LZWANG的博客
sed语法
基本语法
Bash |
---|
| sed [option] 'command' filename
|
命令参数选项
参数 |
说明 |
-n |
安静模式,加上此参数不会将处理后的文本结果输出到屏幕 |
-i |
修改原文件,加上此参数sed将直接对原始文件进行修改 |
-e |
一次对目标文件执行多条子命令 |
-f |
执行指定文件sed脚本命令 |
-r |
使用扩展正则表达式ERE,而不是基本正则表达式BRE |
提示
在macOS系统中,如果使用 sed -i
命令,相比于Linux系统需要在 -i
参数后加上一个空字符串,不然将无法修改源文件。
如在Linux上 sed -i 's/a/b/g' file.txt
那么在macOS上需要改为 sed -i '' 's/a/b/g' file.txt
定址操作
默认情况下sed会对文件的每一行进行操作,如果需要处理特殊的几行文本,需要进行定址操作。
假设我们有一个名为test.txt
的文件,内容如下
Text Only |
---|
| hello world
hello here
hello there
hello world
|

如果不使用定址,直接使用sed执行如下替换操作
Bash |
---|
| sed 's/hello/hi/g' test.txt
|
输出为
数字定址
数字定址即使用数字行数来确定要操作的行
某一行
Bash |
---|
| # 将第3行进行替换
sed '3s/hello/hi/g' test.txt
|
连续几行
Bash |
---|
| # 将第1-3行进行替换
sed '1,3s/hello/hi/g' test.txt
|
从某一行起的后几行
Bash |
---|
| # 将第3行及后4行(第3-7行)进行替换
sed '3,+4s/hello/hi/g' test.txt
|
macOS系统

Linux系统
除去某一行的剩余行
Bash |
---|
| # 将第3行之外其余所有行进行替换
sed '3!s/hello/hi/g' test.txt
|
正则定址
正则定址即使用正则表达式来确定要操作的行。
匹配特定字符串
Bash |
---|
| # 匹配到带有world的行并删除
sed '/world/d' test.txt
|
匹配空行
Bash |
---|
| # 删除空行
sed '/^$/d' test.txt
|
匹配字符串1和字符串2之间的所有行
Bash |
---|
| # 删除here结尾至world结尾行之间的所有行
sed '/here$/,/world$/d' test.txt
|
子命令
替换字符串子命令s
基本语法:[address]s/pattern/rep/flags
将示例的文本文件改写如下:
Text Only |
---|
| hello world hello
hello here hello hello hello
hello there
hello world
|
只替换行内匹配到的第一个
Bash |
---|
| # 将每一行第一个hello换成hi
sed 's/hello/hi/' test2.txt
|
替换行内所有匹配到的
Bash |
---|
| # 将每一行所有hello换成hi
sed 's/hello/hi/g' test2.txt
|
只替换某一个匹配到的
Bash |
---|
| # 将每一行第二个hello换成hi
sed 's/hello/hi/2' test2.txt
|
替换某一个之后匹配到的
Bash |
---|
| # 将每一行第二个之后(第3个及以后)hello换成hi
sed 's/hello/hi/3g' test2.txt
|
macOS

Linux
在行首添加内容
Bash |
---|
| # 将每一行行首添加123字符串
sed 's/^/123/g' test2.txt
|
在行尾添加内容
Bash |
---|
| # 将每一行行尾添加123字符串
sed 's/$/123/g' test2.txt
|
匹配多个字符串并替换
Bash |
---|
| # 将1-3行的hello替换成hi,且第3行后的world替换为tomorrow
sed '1,3s/hello/hi/g; 3,$s/world/tomorrow/g' test2.txt
# 等价命令
sed -e '1,3s/hello/hi/g' -e '$s/world/tomorrow/g' test2.txt
|
将匹配到的字符串改写
Bash |
---|
| # 将hello两端加上双引号
sed 's/hello/"&"/g' test2.txt
|
只打印修改的行
Bash |
---|
| # 将hello两端加上双引号,并只打印改动的行 /p
sed -n 's/hello/"&"/p' test2.txt
|
匹配时忽略大小写
Bash |
---|
| # 将hello两端加上双引号,并只打印改动的行 /i
sed -n 's/hello/"&"/i' test2.txt
|
macOS

Linux
替换行子命令c
此命令用于将整行替换为自己的文本。
替换所有行
Bash |
---|
| # 将所有行替换为12345
sed 'c 12345' test2.txt
|
替换某几行
Bash |
---|
| # 将1-3行替换为12345(三行变成一行)
sed '1,3c 12345' test2.txt
|
分别替换几行
Bash |
---|
| # 将1-3行分别替换为12345(使用换行符解决)
sed '1,3c 12345\n12345\n12345' test2.txt
|
追加行子命令a
追加所有行
Bash |
---|
| # 将所有行后追加一行12345
sed 'a 12345' test2.txt
|
追加某几行
Bash |
---|
| # 将1-3行后追加一行12345
sed '1,3a 12345' test2.txt
|
插入行子命令i
可以视作追加的反操作(即在指定行前追加行)
Bash |
---|
| # 将1-3行前插入一行12345
sed '1,3i 12345' test2.txt
|
删除行子命令d
删除指定几行
Bash |
---|
| # 将1-3行删除
sed '1,3d' test2.txt
|
删除正则匹配行
Bash |
---|
| # 将there结尾的行删除
sed '/there$/d' test2.txt
|
设置行号子命令=
在行上方插入行号
Bash |
---|
| # 在1-3行上插入行号
sed '1,3=' test2.txt
|
在行前插入行号
Bash |
---|
| # 在所有行前插入行号,与行内容间隔两个空格
sed '=' test2.txt | sed 'N;s/\n/ /'
|
参考