短视频开发 WorldCloud oracle file inheritance 数据库设计规范 java手机验证码 hadoop组件 centos7安装gcc css选择器有几种 docker保存镜像 python对象 java语言学习 java变量类型 java安装 java数组排序 java特性 java判断 摩尔斯电码翻译器 idea重命名快捷键 手机知识 临时会话 暴力猴插件 处理器虚拟化技术 ps怎么画漫画 facetime要钱吗 jsp源代码 ps高手教程 上单艾克出装 微信问卷调查怎么做 谷歌浏览器升级 大话5g OPPO投屏 求字符串长度的函数 illustrator下载 fleaphp 极光迪莫 征战者加点 手机手写怎么设置 店透视插件
当前位置: 首页 > 学习教程  > 编程语言

Linux之Sed命令44道应用练习题实战

2020/8/11 20:14:03 文章标签:

Sed用法及习题精选

文章目录

    • Sed用法及习题精选
    • Sed工作原理
    • 习题1
    • 习题2
    • 习题3
    • 习题4
    • 习题5

Sed工作原理

  • 原理

    1. 读入新的一行内容到模式空间(pattern space);
    2. 从指定的操作指令中取出第一条指令,判断是否匹配pattern;
    3. 如果不匹配,则忽略后续的编辑命令,回到第2步继续取出下一条指令;
    4. 如果匹配,则针对缓存的行执行后续的编辑命令(补充:执行完后,才进行默认输出[可以被-n选项抑制掉],然后再清空模式空间);完成后,回到第2步继续取出下一条指令;
    5. 当所有指令都应用之后,输出缓存行的内容;回到第1步继续读入下一行内容;
    6. 当所有行都处理完之后,结束;
  • 命令格式

    syntax:sed [option]… {Script} [FILE]…**

  • 常用格式

    sed 选项 地址编辑命令 文件

  • [option]

    -n : 不输出模式空间中的内容至屏幕,即关闭不能被模式匹配到的行到标准输出

    -e : 多想编辑命令一次执行

    -f FILE : 将编辑指令写入文件,调用FILE

    -r : 支持扩展正则表达式元字符

    -i : 直接修改原文件

    -i.bak : 修改源文件,但是会生成备份文件为.bak的文件

  • 地址

    1. 空地址:即对全文进行处理

    2. 单地址(line-address)

    3. 步进地址表示法

      1~2 : 所有奇数行: sed -n ‘1~2p’ test
      2~2 : 所有偶数行: sed -n ‘2~2p’ test

    4. 地址对(address)

      N,M : 第N到M行

      N,+M : 从N行向下M行

      N,/pattern/ : 从N到正则匹配到的行

      /pattern1/,/pattern2/ : 从模式1到模式2匹配到的行

      $ : 表示最后一行

  • 模式空间(基础命令)

    1. d : 删除模式空间内容

    2. [line-address]a\STRING : append,在指定行下一行追加内容

    3. [line-address]i\STRING : insert,在指定行上一行追加内容

    4. c\STRING : change,改变指定行内容

    5. p : print,打印模式空间的内容

    6. l : list,输出行控制符

    7. = : 输出行号

    8. s/RegExp/REPLACE/g : search,搜索与替换,"/"可以换成其他符号:#@%…

    • 在s///中使用分组及后向引用
    • eg: sed -r ‘s/i love (\S+) and (\S+)/\1 love \2/’ /tmp/test
    1. n : next,读取下一行

    2. y/abc/xyz/ : 转换字符,a转成x,b转成y,c转成y,一一对应转换

    3. w FILE : write,保存内容

      • [line-address]r FILE : read,将文件内容读取到指定行
    4. [line-address]q : quit,读取到匹配行之后退出

  • 模式空间(高级命令)

    1. N : 将下一行读到模式空间,用\n连接上一行 (注意:是模式空间同一行)
    2. P : 输出上一行内容
    3. D : 删除上一行内容,并且继续执行指令 保持空间命令
    4. h/H : hold,将模式空间内容复制(h),通过\n追加(H)到保持空间
    5. g/G : get,将保持空间内容复制(g),通过\n追加(G)到模式空间
    6. x : exchange,将保持空间内容和模式空间内容交

习题1

  1. 所有以192.168.0.1开头的行都会被替换成它自己加localhost

    [root@ ~ 10:42:37]#echo -e '192.168.0.1 xixi\naaa\n192.168.0.1\nbbb'|   \
     sed -r 's/192.168.0.1/&localhost/g'   #-r 支持正则表达式
    192.168.0.1localhost xixi
    aaa
    192.168.0.1localhost
    bbb
    
  2. 替换 digit 数字 ,内容为 相同数字

    [root@ ~ 10:42:37]#cat test
    aa digit3
    digit44bb
    12digitb 
    [root@ ~ 10:42:37]# sed -r 's/digit([0-9])/\1/g' test
    aa 3						#利用后向引用和s///进行替换
    44bb
    12digitb
    
  3. love被标记为\1,所有loverable会被替换成lovers,并打印出来

    [root@ ~ 10:42:37]#cat test
    loverabl1
    lover
    loverable
    [root@ ~ 10:58:46]#sed -r 's/(love)rable/\1rs/g' test
    loverabl1						#同样使用后向引用
    lover
    lovers
    
  4. 使用n或p打印奇数行或偶数行(列出4种方法)

    #奇数行
    echo -e "a\nb\nc\nd\ne"|sed -n 'P;N'
    echo -e "a\nb\nc\nd\ne"|sed -n 'p;n'
    echo -e "a\nb\nc\nd\ne"|sed -n '1~2p'
    #偶数行
    echo -e "a\nb\nc\nd\ne"|sed -n 'n;p'
    echo -e "a\nb\nc\nd\ne"|sed -n '2~2p'
    

习题2

  1. 对于包含test到west之间的行,每行加上字符串’aaa bbb’

    [root@ ~/test 04:12:45]#cat test
    a test hehe west xixi 
    test haha wes .
    [root@ ~ 11:15:37]#sed -r 's/(test.*west.*$)/\1aaa bbb/g' test
    a test hehe west xixi aaa bbb			#使用后向引用 \1 指代前面括号里的内容
    test haha wes .
    
  2. 查找包含line1的行到包含line2的行之间的所有aa bbb替换成AA BBB

[root@ ~ 10:42:37]#cat test 
aa bbb line1 aa 
 aa bbb 
 cc aa bbb 
 line2  
 aa bbb 
 line1
[root@ ~ 11:20:23]#sed '/line1/,/line2/s/aa bbb/AA BBB/g' test
AA BBB line1 aa 
 AA BBB 
 cc AA BBB 
 line2  
 aa bbb 
 line1 
  1. 匹配关键字并显示后几行
  • 显示第一次匹配到的3到最后一行输出

    [root@ ~ 10:42:37]#cat test 
    1
    2
    3
    4
    5
    6
    [root@ ~ 11:34:17]#echo -e '1\n2\n3\n4\n5\n6' |sed -n '/3/,$p'
    3
    4
    5
    6
    
  • 显示第一次匹配到的3到向下两行输出

    [root@ ~ 10:42:37]#cat test
    1
    2
    3
    4
    5
    6
    [root@ ~ 11:48:19]#sed -n  '/3/{N;N;p}'  test
    3			#利用两次N将后两行追加到模式空间(同一行,\n分隔离),并打印,默认抑制
    4
    5
    
  1. 逆序显示文本内容

    [root@ ~ 12:09:52]#echo -e '1\n2\n3\n4\n5\n6' |sed -n '1!G;h;$p'
        
    6		#处理行不是第一行,就从保持空间的内容追加到模式空间(形成最新的逆序串)
    5		#然后这个串再覆盖保持空间里
    4		#当处理完最后一行后,打印保持空间的内容
    3
    2
    1
    [root@ ~/test 04:22:22]#sed -n '1h;1!{G;h};$p' test #也可以
    
  2. 取出文本中最后一行

    [root@ ~ 12:11:17]#echo -e '1\n2\n3\n4\n5\n6' |sed -n '$p'
    6								#最后一行,打印
    
  3. 删除原有的所有空白行,而后为所有的非空白行后添加一个空白行

    [root@ ~ 09:41:39]#echo -e 'a\n\nb\n\nc\nd'
    a
    
    b
    
    c
    d
    [root@ ~ 09:41:32]#echo -e 'a\n\nb\n\nc\nd'|sed -n -r '/.+/{G;p}'
    a
    
    b
    
    c
    
    d
    
    
  4. 在原有的每行后方添加一个空白行

    [root@ ~ 09:42:27]#echo -e 'a\nb\nc\nd'
    a
    b
    c
    d
    [root@ ~ 09:42:06]#echo -e 'a\nb\nc\nd'|sed -n 'G;p'
    a
    
    b
    
    c
    
    d
    
    
  5. 显示最后一行的行号,一般可用于显示文本的总行数

    [root@ ~ 09:50:43]#echo -e 'a\n\n\nb\n\n\nc\nd'
    a
    
    
    b
    
    
    c
    d
    [root@ ~ 10:00:23]#echo -e 'a\n\n\nb\n\n\nc\nd'|sed -n '$=' #打印尾行行号
    8
    
  6. 显示所有行的行号,但空行不显示行号

    [root@ ~ 09:50:43]#echo -e 'a\n\n\nb\n\n\nc\nd'
    a
    
    
    b
    
    
    c
    d
    [root@ ~ 10:02:19]#echo -e 'a\n\n\nb\n\n\nc\nd'|sed -n '/^$/!='
    1													#不是空行就打印行号
    4
    7
    8
    

习题3

  1. 删除所有的空行,并在每行后面增加一个空行

    [root@ ~/test 04:09:19]#echo -e "\na\n\n\nb\n\nc"
    
    a
    
    
    b
    
    c
    [root@ ~/test 04:12:40]#echo -e "\na\n\n\nb\n\nc"|sed -r -n '/^$/!{s/(.*)/\1\n/;p}'  #对不是空行的情况尾部增加一个换行符,并且打印,别忘了抑制默认输出
    a
    
    b
    
    c
    
    
  2. 在查找到的行前增加一个空行

    [root@ ~/test 04:02:36]#echo -e "a\nb\nc\nd\nd\ne\nf"
    a
    b
    c
    d
    d
    e
    f
    [root@ ~/test 04:01:56]#echo -e "a\nb\nc\nd\nd\ne\nf"|				\     sed -r 's/(^c.*)/\n\1/'
    a
    b
    
    c
    d
    d
    e
    f
    
  3. 统计文本的行数

    [root@ ~/test 03:58:32]#echo -e "a\nb\nc\nd\nd\ne\nf"|sed -n '$='
    7
    
  4. 将没一行的行首的空白字符(空格,制表符)删除

    [root@ ~/test 03:55:27]#echo -e "   a\n\ta\ta\n a\na\ta"
       a
    	a	a
     a
    a	a
    [root@ ~/test 03:55:53]#echo -e "   a\n\ta\ta\n a\na\ta"|			\	     sed -r 's/^( +|\t+)//'
    a
    a	a
    a
    a	a
    
  5. 将文本中的’aaa’,‘bbb’,‘ccc’都替换为’ttt’

    [root@ ~/test 03:49:50]#echo -e "aaa bbb\nbbb\nccc aaa"
    aaa bbb
    bbb
    ccc aaa
    [root@ ~/test 03:52:06]#echo -e "aaa bbb\nbbb\nccc aaa"|			\        	sed -r 's/aaa|bbb|ccc/ttt/g'    #全局替换,若缺少g则每行最多替换第一个满足的字串 
    ttt ttt
    ttt
    ttt ttt
    
  6. 将’yes’替换成’no’,并且只在行中未出现字串’hello’的情况下替换

    [root@ ~/test 03:49:09]#echo -e "hello yes sir\nhi yes sir"
    hello yes sir
    hi yes sir
    [root@ ~/test 03:49:39]#echo -e "hello yes sir\nhi yes sir"|			\    sed  -r '/hello/!s/yes/no/'
    hello yes sir
    hi no sir
    
  7. 将每行的字符逆序显示

    [root@ ~/test 04:12:45]#cat test
    BEACH HAHA AMAZON
    ALIBABA HAHA TENCENT
    PINGLINGLAB HAHA GDUT
    [root@ ~/test 04:22:22]#sed -n '1h;1!{G;h};$p' test
    NOZAMA AHAH HCAEB
    TNECNET AHAH ABABILA
    TUDG AHAH BALGNILGNIP
    
  8. 将数字’1234567’显示为1,234,567

    [root@ ~/test 03:46:11]#echo '1234567'|sed  's/1/1,/;s/4/4,/'
    1,234,567
    
  9. 模拟 tail -1 命令的效果

    [root@ ~/test 03:33:01]#cat error.log
    APPLE XIXI GOOGLE
    BEACH HAHA AMAZON
    FACEBOOK XIXI NETEASE
    ALIBABA HAHA TENCENT
    ORICLE XIXI SUN
    PINGLINGLAB HAHA GDUT
    [root@ ~/test 03:36:40]#sed -n '$!d;$p' error.log  #不是尾行就删除,是就打印
    PINGLINGLAB HAHA GDUT
    
  10. 将如下内容通过sed处理

aaa
bbb
ccc
ddd
eee
fff

变为

 aaa bbb
 ccc ddd
 eee fff
[root@ ~/test 02:59:42]#echo -e 'aaa\nbbb\nccc\nddd\neee\nfff'|sed -n 'N;s/\n/ /;p'
aaa bbb
ccc ddd
eee fff

习题4

  1. 将error.log中匹配到的内容保存至某文件

    [root@ ~/test 03:33:01]#cat error.log
    APPLE XIXI GOOGLE
    BEACH HAHA AMAZON
    FACEBOOK XIXI NETEASE
    ALIBABA HAHA TENCENT
    ORICLE XIXI SUN
    PINGLINGLAB HAHA GDUT
    [root@ ~/test 03:33:06]#sed '/HAHA/w ./test' error.log   										#含有HAHA一行就保存到test文件里
    [root@ ~/test 03:33:48]#cat ./test
    BEACH HAHA AMAZON
    ALIBABA HAHA TENCENT
    PINGLINGLAB HAHA GDUT
    
  2. 将文件中的内容读入到匹配的内容后面

    [root@ ~/test 03:03:04]#cat test
    APPLE XIXI GOOGLE
    BEACH HAHA AMAZON
    FACEBOOK XIXI NETEASE
    ALIBABA HAHA TENCENT
    ORICLE XIXI SUN
    PINGLINGLAB HAHA GDUT
    [root@ ~/test 03:25:39]#cat test|sed -r -n '/HAHA/p;/HAHA/!H;$g;s/^\n//;$p' #以HAHA开头打印,不以HAHA开头追加到扩展空间
    BEACH HAHA AMAZON				 #处理到最后一行,将扩展空间内容覆盖到模式空间
    ALIBABA HAHA TENCENT			 #将模式空间开头的换行符置空
    PINGLINGLAB HAHA GDUT			 #将模式空间打印,打印内容是不以HAHA开头的行
    APPLE XIXI GOOGLE
    FACEBOOK XIXI NETEASE
    ORICLE XIXI SUN
    
    
  3. 打印匹配到的内容,并显示行号

    [root@ ~/test 01:31:53]#cat sedtest |sed -r -n '/ddd$/{=;p}'
    7			#行号
    7ddd		#行号对应内容
    14
    14aaaddd
    21
    21aaa ddd
    
  4. 删除匹配到的行的下一行

    [root@ ~/test 01:20:14]#echo -e '1\n2\n3\n4\n5\n6\n7\n8'|sed -n '/^4/{h;n;g};p'
    1
    2
    3
    4
    6
    7
    8
    
  5. 删除匹配到的行和下一行

    [root@ ~/test 01:23:06]#echo -e '1\n2\n3\n4\n5\n6\n7\n8'|sed  '/^4/{N;d}'
    1
    2
    3
    6
    7
    8
    
  6. 删除文件每行中的第一个字

    [root@ ~/test 01:25:39]#cat sedtest |sed -r 's/^.//g'
    
  7. 删除文件每行的第二个字符

    [root@ ~/test 01:27:10]#cat sedtest |sed -r 's/(.)(.)(.*)/\1\3/g'
    
  8. 删除文件每行的最后一个字符

    [root@ ~/test 01:28:11]#cat sedtest |sed -r 's/(.*)./\1/g'
    
  9. 删除文件每行的倒数第二个字符

    [root@ ~/test 01:28:11]#cat sedtest |sed -r 's/(.*).(.)/\1\2/g'
    
  10. 删除每行的最后一个单词

    [root@ ~/test 02:47:38]#cat test
    i have a dream.
    this is a homework .
    why don't you join Pinginglab?
    [root@ ~/test 02:54:30]#cat test|sed -r 's/(.*) ([a-zA-Z]+)(.)/\1\3/g'
    i have a.
    this is a .
    why don't you join?
    

习题5

  1. 删除一个文件中的所有的数字

    [root@ ~/test 10:35:00]#cat sedtest 
    aaa 11bb22
    bb2 33cc44
    aaaaaaaaaa
    [root@ ~/test 10:35:56]#sed -r 's/[0-9]//g' sedtest
    aaa bb
    bb cc
    aaaaaaaaaa
    
  2. 将时间格式 yy/mm/dd 的日期换成 yy:mm:dd 的格式( data 命令实现:如2016/08/15变成 2016:08:16)

    [root@ ~/test 10:38:46]#cat sedtest
    a2016/05/31a
    a 11/01/01a
    3/04/30 a
    [root@ ~/test 10:46:17]#sed  -r 's/\b([0-9]+)\/([0-9]{2})\/([0-9]{2})\b/\1:\2:\3/g' sedtest 
    a2016/05/31a
    a 11/01/01a
    3:04:30 a
    
  3. 显示奇数行

    [root@ ~/test 10:46:37]#cat sedtest 
    a2016/05/31a
    a 11/01/01a
    3/04/30 a
    [root@ ~/test 11:05:36]#cat sedtest | sed  -n '1~2p'
    a2016/05/31a
    3/04/30 a
    
  4. 删除模式一到模式二匹配到的行

    [root@ ~/test 11:07:52]#echo -e '1\n2\n3\n4\n5\n6' 
    1
    2
    3
    4
    5
    6
    [root@ ~/test 11:07:45]#echo -e '1\n2\n3\n4\n5\n6' |sed -r '/^2/,/^4/{d}'
    1
    5
    6
    
  5. 从指定行开始,每隔2行显示一次

    [root@ ~/test 11:07:52]#echo -e '1\n2\n3\n4\n5\n6' 
    1
    2
    3
    4
    5
    6
    [root@ ~/test 11:22:13]#echo -e '1\n2\n3\n4\n5\n6' |sed -n '2~3p'
    2
    5
    
  6. 删除文中的最后两行

    [root@ ~/test 11:38:53]#echo -e '1\n2\n3\n4\n5\n6'
    1
    2
    3
    4
    5
    6
    [root@ ~/test 05:14:34]#echo -e "1\n2\n3\n4\n5" |		\				sed  -r -n 'H;$g;$s/\n(.*)\n(.*)\n(.*)/\1/;$p'
    1
    2
    3
    
  7. 删除文中的空行

    [root@ ~/test 11:44:17]#echo -e '1\n\n2\n\n3\n4\n\n5\n6'
    1
    
    2
    
    3
    4
    
    5
    6
    [root@ ~/test 11:44:22]#echo -e '1\n\n2\n\n3\n4\n\n5\n6'|sed '/^$/d'
    1
    2
    3
    4
    5
    6
    
  8. 每隔5行增加一个空行

    [root@ ~/test 11:58:39]#echo -e '1\n2\n3\n4\n5\n6\n7\n8'
    1
    2
    3
    4
    5
    6
    7
    8
    [root@ ~/test 12:01:17]#echo -e '1\n2\n3\n4\n5\n6\n7\n8'|sed -r -n '0~5G;p'		#从开始起每逢五行从扩展空间追加一个换行符到模式空间,并打印模式空间内容
    1
    2
    3
    4
    5
    
    6
    7
    8
    
  9. 不显示指定字符开始的行

    [root@ ~/test 12:48:09]#echo -e '1\n2\n3\n4\n5\n6\n7\n8'|sed -r -n '/^4/d;p'			#不显示以4开头的行
    1
    2
    3
    5
    6
    7
    8
    
  10. 查找文件中1到20行之间,同事将’aaa’替换为’AAA’,‘ddd’替换成’DDD’

    [root@ ~/test 12:52:54]#sed -r '1,20y/aaa/AAA/;1,20y/ddd/DDD/' sedtest 
    1
    2
    3
    4
    5DDD AAA
    6
    7DDD
    8
    9
    10AAA
    11
    12
    13
    14AAADDD
    15
    16
    17
    18
    19
    20
    21aaa ddd   #可以看到哦第21行没有被替换
    

本文链接: http://www.dtmao.cc/news_show_100305.shtml

附件下载

相关教程

    暂无相关的数据...

共有条评论 网友评论

验证码: 看不清楚?