文章下方附学习资源 请自主领取

哈喽,老吴这几天在知乎上看到了一个问题:

学习 shell 有什么好书推荐??

最高赞的答案里推荐的《sed and awk 101 hacks》引起了我的注意。

虽然平时调试分析时,经常用 Sed 或 Awk 对 log 进行一些简单的排版处理。

但事实上,老吴一直没有好好的发挥 Sed 和 Awk 这两个 UNIX 文本处理神器。

趁这个周末有时间,我快速地学习了一下《sed and awk 101 hacks》,发现这真是一本神奇的书,整本书就是对 1 个文件进行各种操作,以这种简单的方式输出了一堆的干货。

由于干货太多,这篇文章我先总结 Sed 相关的知识,Awk 留到后面再写。

由于是英文书,为了避免产生歧义,许多术语我将使用英文来表达。

开始 Enjoy 吧!

Sed 是什么?

Sed 是 的简称,即文本流编辑器。

macsed_sed_sed命令

它可以对文件执行许多操作,例如搜索、查找和替换、插入或删除。

在 UNIX 中,Sed 命令最常见的用途是查找和替换。

通过使用 Sed,我们甚至可以在不打开文件的情况下编辑文件,这比首先在 VI 编辑器中打开该文件然后更改它要快得多。

Sed 怎么用?

接下来,所有的操作都基于下面这个文件:

$ vi employee.txt
101,John Doe,CEO
102,Jason Smith,IT Manager
103,Raj Reddy,Sysadmin
104,Anand Ram,Developer
105,Jane Miller,Sales Manager

Sed 工作流?

sed_macsed_sed命令

Sed 每次会读取一行文本到 space (类似缓冲区)里,然后执行用户指定的命令 (sed-),然后打印出 space 的内容并清空 space,循环执行上面的 3 个步骤。

语法:

sed [options] {sed-commands} {input-file}

一个具体的例子:

# 等效于 cat employee.txt
$ sed -n 'p' employee.txt
101,John Doe,CEO
102,Jason Smith,IT Manager
103,Raj Reddy,Sysadmin
104,Anand Ram,Developer
105,Jane Miller,Sales Manager

-n 对应 。Sed 默认会打印 space 里的内容,-n 表示禁止打印

'p' 对应 sed-,p 命令表示打印。

.txt 对应 input-file。

执行多条命令:

# 筛选出以 101 或 103 开头的行
$ sed -n -e '/^101/ p' -e '/^103/ p' employee.txt
101,John Doe,CEO
103,Raj Reddy,Sysadmin

嵌入式物联网需要学的东西真的非常多,千万不要学错了路线和内容,导致工资要不上去!

无偿分享大家一个资料包,差不多150多G。里面学习内容、面经、项目都比较新也比较全!某鱼上买估计至少要好几十。

点击这里找小助理0元领取:嵌入式物联网学习资料(头条)

sed命令_sed_macsed

macsed_sed_sed命令

打印操作(p 命令):

我们可以在 p 命令前加一些修饰参数,用于指定 range 或 range。

# 只打印第 2 行
$ sed -n '2 p' employee.txt
102,Jason Smith,IT Manager

# 打印第 1 到 4 行
$ sed -n '1,4 p' employee.txt
101,John Doe,CEO
102,Jason Smith,IT Manager
103,Raj Reddy,Sysadmin
104,Anand Ram,Developer

# 打印第 2 到最后一行
$ sed -n '2,$ p' employee.txt
102,Jason Smith,IT Manager
103,Raj Reddy,Sysadmin
104,Anand Ram,Developer
105,Jane Miller,Sales Manager

# 打印匹配 “Jane” 的行
$ sed -n '/Jane/ p' employee.txt
105,Jane Miller,Sales Manager

# 打印从匹配 “Raj” 起始,直到文件末尾的行
$ sed -n '/Raj/,$ p' employee.txt
103,Raj Reddy,Sysadmin
104,Anand Ram,Developer
105,Jane Miller,Sales Manager

# 打印从匹配 “Raj” 起始,直到匹配 “Jane” 的行
$ sed -n '/Raj/,/Jane/ p' employee.txt
103,Raj Reddy,Sysadmin
104,Anand Ram,Developer
105,Jane Miller,Sales Manager

删除操作(d 命令):

删除操作和打印操作很类似,只是将命令 p 换成命令 d

sed 'd' employee.txt
sed '2 d' employee.txt
sed '1,4 d' employee.txt
sed '2,$ d' employee.txt
sed '1~2 d' employee.txt
sed '/Manager/ d' employee.txt
sed '/Jason/,4 d' employee.txt
sed '/Raj/,$ d' employee.txt
sed '/Raj/,/Jane/ d' employee.txt

写操作(w命令)

Sed 默认是将 space 的数据写到 ,用 w 命令可以将数据写到指定文件。

sed -n 'w output.txt' employee.txt
sed -n '2 w output.txt' employee.txt
sed -n '1,4 w output.txt' employee.txt
sed -n '2,$ w output.txt' employee.txt
sed -n '1~2 w output.txt' employee.txt
sed -n '/Jane/ w output.txt' employee.txt
sed -n '/Jason/,4 w output.txt' employee.txt
sed -n '/Raj/,$ w output.txt' employee.txt
sed -n '/Raj/,/Jane/ w output.txt' employee.txt

替换操作(s 命令):

Sed 最牛掰的命令就是替换,先看语法:

sed '[address-range|pattern-range] s/original-
string/replacement-string/[substitute-flags]' inputfile

range 用于定位,是可选参数;

flags 用于修饰替换的行为,是可选参数;

先看 2 个最简单的例子:

# 将所有的 “Manager” 都替换为 "Director"
$ sed 's/Manager/Director/' employee.txt
101,John Doe,CEO
102,Jason Smith,IT Director
103,Raj Reddy,Sysadmin
104,Anand Ram,Developer
105,Jane Miller,Sales Director

# 将包含 “Sales” 的行里的 "Manager" 替换成 "Director"
$ sed '/Sales/s/Manager/Director/' employee.txt
101,John Doe,CEO
102,Jason Smith,IT Manager
103,Raj Reddy,Sysadmin
104,Anand Ram,Developer
105,Jane Miller,Sales Director

默认情况下,s 命令只会替换一行中第一处匹配的地方,想全局替换,要使用 Flag:

# 只替换第一处
$ sed 's/a/A/' employee.txt
101,John Doe,CEO
102,JAson Smith,IT Manager
103,RAj Reddy,Sysadmin
104,AnAnd Ram,Developer
105,JAne Miller,Sales Manager
# 全局替换
$ sed 's/a/A/g' employee.txt
101,John Doe,CEO
102,JAson Smith,IT MAnAger
103,RAj Reddy,SysAdmin
104,AnAnd RAm,Developer
105,JAne Miller,SAles MAnAger

Flag 可以用于指定要处理第几处的匹配项:

# 只替换第 2 个 'a'
$ sed 's/a/A/2' employee.txt
101,John Doe,CEO
102,Jason Smith,IT MAnager
103,Raj Reddy,SysAdmin
104,Anand RAm,Developer
105,Jane Miller,SAles Manager

还有一些用得比较少的 Flag:

# Print Flag (p flag) 用于打印匹配行
$ sed -n 's/John/Johnny/p' employee.txt
101,Johnny Doe,CEO
# Write Flag (w flag) 用于写入
$ sed -n 's/John/Johnny/w output.txt' employee.txt
$ cat output.txt
101,Johnny Doe,CEO
# Ignore Case Flag (i flag) 用于忽略大小写
$ sed 's/john/Johnny/i' employee.txt

多个 Flag 可以组合在一起使用:

$ sed -n 's/Manager/Director/gipw output.txt'
employee.txt
102,Jason Smith,IT Director
105,Jane Miller,Sales Director

Sed 替换操作默认的分隔符是 '/',如果要处理的文本含 有 '/' 的话,可以换一个分隔符:

# 将 /usr/local/bin 替换成 /usr/bin
sed 's|/usr/local/bin|/usr/bin|' path.txt
sed 's^/usr/local/bin^/usr/bin^' path.txt
sed 's@/usr/local/bin@/usr/bin@' path.txt
sed 's!/usr/local/bin!/usr/bin!' path.txt

引用和正则表达式:

& 可以用来引用匹配项:

# 给 ID 号加上 []
$ sed 's/^[0-9][0-9][0-9]/[&]/g' employee.txt
[101],John Doe,CEO
[102],Jason Smith,IT Manager
[103],Raj Reddy,Sysadmin
[104],Anand Ram,Developer
[105],Jane Miller,Sales Manager

跟在正则表达式中一样,sed 中也可以使用分组。分组以 '(' 开始,以 ')' 结束。分组后就可以按组来引用了:

$ sed 's/([^,]*),([^,]*),([^,]*).*/1,3/g' employee.txt
101,CEO
102,IT Manager
103,Sysadmin
104,Developer
105,Sales Manager

[^,] 表示除了',' 之外的任意字符,* 表示0个或者多个。

第 1 个分组 ([^,]*) ,匹配雇员 ID,在后面用 '1' 来引用。

第 3 个分组 ([^,]*) ,匹配雇员职位,在后面用 '3' 来引用。

Sed 一般搭配正则表达式使用,关于正则表达式的用法,则需要再写一篇文章才能说清楚。

到此,Sed 比较常用的用法就介绍完毕了。

总结

Sed 是 UNIX 世界的两大文本处理神器之一, 它能帮你对文本进行删除、替换等操作,熟练掌握它将大大增加你的文本处理能力。

使用 Sed 需要记住下面几个概念:

Flow,Sed 的工作流程;

,Sed 支持哪些命令?

Flag,Sed 命令支持哪些 flag?

正则,Sed 如何搭配正则表达式?

最后,建议读者朋友们读完本文后,亲自去看看 《sed and awk 101 hacks》 这本书,肯定会跟我一样受益匪浅的。

引用书里的一句话:

Your UNIX and Linux Life with Sed and Awk.

———END———
限 时 特 惠: 本站每日持续更新海量各大内部创业教程,永久会员只需109元,全站资源免费下载 点击查看详情
站 长 微 信: nanadh666

声明:1、本内容转载于网络,版权归原作者所有!2、本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。3、本内容若侵犯到你的版权利益,请联系我们,会尽快给予删除处理!