Linux学习总结(二十)正则三剑客之sed

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Linux学习总结(二十)正则三剑客之sed相关的知识,希望对你有一定的参考价值。

sed
流式编辑器,针对文档的行来操作的

一 查找打印

1.打印某行
格式: sed -n ‘n‘p filename 单引号内的n代表数字,表示第几行
例如:打印第二行
sed -n ‘2‘p /etc/passwd
也可以指定区间,比如打印前三行
sed -n‘1,3‘p /etc/passwd
打印所有的行
sed -n ‘1,$‘p /etc/passwd

  1. 打印包含某个字符串的行,相当于grep
    格式 : sed -n ‘/字符串/‘p filename
    例如 sed -n ‘/root/‘p /etc/passwd
    -e 可以实现在一条命令中对文档进行多次操作,意思是针对某个文档并行操作几次,两个-e,就是两次操作,依次类推。例如:
    sed -e ‘1,3‘p -e ‘/root/‘p -n /etc/passwd
    该命令等价于 sed -n ‘1,3‘p /etc/passwd;sed -n ‘/root/‘p /etc/passwd
  2. 我们刚学过grep 有个-i 选项,可以忽略大小写匹配,sed 同样可以,加一个I选项。例如
    sed -n ‘/root/‘Ip /etc/passwd

    二 删除

    1.删除指定的行,直接举例
    sed ‘1,3‘d /etc/passwd 删除前三行,剩余的行会在屏幕打印
    2.删除根据字符串查找出的行
    sed ‘/root/‘d /etc/passwd 删除带有root的行,显示剩余的行
    3.-i 选项可以直接操作源文件。那么我们拷贝一份/etc/passwd再操作
    cp /ect/passwd ./test.txtt
    sed -i ‘1,3‘d test.txt

    三 查找替换

    格式为: sed ‘1,n s/new/old/g‘ filename
    1,n n为数字,指定要替换的区域
    s 替换标识符
    new 用来替换的字符串
    old 将被替换的字符串
    g 标示全局替换
    1.将上面的test.txt文件,前10行中的root全部替换为boot
    sed ‘1,10 s/root/boot/g‘ test.txt 对于该需求我们还可以用正则,例如
    sed ‘1,10 s/ro+t/boot/g‘ test.txt -r 我们发现我们多用了一个-r,原因是
    sed无法直接识别+,它的作用类似于我们grep用的-E选项,当然我们也可以用转意符
    技术分享图片
    2.将test.txt中以:号分割的第一段和最后一段交换位置
    该问题的重点是我们怎么用正则表达要交换的字符串,标示出的字符串要怎么交换,既让目标位置交换,又不破坏其他字符。我们给出思路和结果
    以:号分割,我们将一行看作三段。
    字符串1:字符串2:字符串3
    字符串1和字符串2,我们可以非冒号字符匹配整个字符串,([^:]+)
    字符串2,我们不对其操作,直接贪婪匹配 (.*)
    那么最后的结果为:

sed ‘s/([^:]+):(.*):([^:]+)/\3:\2:\1/g‘ test.txt -r
我们打印前三行看下结果:
技术分享图片
3.把test.txt中英文字母全删除。
也就是把英文字母全部找出来替换为空。
sed ‘s/[a-zA-Z]//g‘ test.txt,我贴出部分结果
技术分享图片
4.在test.txt 文件中行首都加上#:字符
分析: 我们同样用替换的办法,被替换对象就是整行内容,我们用贪婪匹配 (.*) 用来替换的部分就是给原来字符行首加上#: 原来字符可以用&标示,也可以用\1标示,因为只有一段就是第一段,结果为:

sed ‘s/(.*)/#:&/g‘ test.txt -r 或者 sed ‘s/(.*)/#:\1/g‘ test.txt -r
技术分享图片
5.删除test.txt 中的所有特殊字符
解读:特殊字符就是非数字非英文字母

sed ‘s/[^0-9a-zA-Z]//g‘ test.txt
技术分享图片
6.把test.txt中出现的第一个单词和最后一个单词调换位置
分析:很显然分为三段处理,第一个单词,我们用字母开头一直匹配完就可以 (^[a-zA-Z]+)
中间一段从非字母开头一直匹配到非字母结束,中间匹配任意字符 ([^a-zA-Z].*[^a-zA-Z])
最后一个单词用字母匹配至末尾就可以 ([a-zA-Z]+$)
最后的结果为:

sed ‘s/(^[a-zA-Z]+)([^a-zA-Z].*[^a-zA-Z])([a-zA-Z]+$)/\3\2\1/g‘ test.txt -r
技术分享图片
7把test.txt中的第一个数字移动到本行末尾
分析:也是分为三段,第一段非数字开头匹配 (^[^0-9]+), 第二段匹配数字([0-9]+)
第三段非数字开头,后面匹配任意到结尾([^0-9].*$),第二段和第三段交换位置就可以了。结果为:

sed ‘s/(^[^0-9]+)([0-9]+)([^0-9].*$)/\1\3\2/g‘ test.txt -r
技术分享图片

以上是关于Linux学习总结(二十)正则三剑客之sed的主要内容,如果未能解决你的问题,请参考以下文章

linux12shell编程 --> 三剑客之sed命令

Linux 学习总结(十九)正则三剑客之grep

Linux三剑客之sed

linux三剑客之sed

Linux之三剑客

Linux文本三剑客之sed