zoukankan      html  css  js  c++  java
  • sed初理多行合并+sed之G、H、g、h使用+sed n/N使用说明

    转载:【shell】sed处理多行合并 - seyjs - 博客园 (cnblogs.com)

    文件格式
    
    table=t1
    name
    owner
    address
    table=t2
    id
    text
    col1
    comment
    col5
    table=t3
    prod_name
    price
    
    要求按table=关键字,将相同的table的列放在同一行,结果为:
    
    table=t1 name owner address
    table=t2 id text col1 comment col5
    table=t3 prod_name price
    
    另外要求只能用sed

    这题我的的想法是先用xargs去掉所有的换行符,然后用sed把table替换成 table。

    可以题目中要求了只能用sed,所以本题的核心就是sed合并行。

    怎么用sed合并行,我用到了保持空间,步骤如下:

    1.如果是第一行,把模式空间替换到保持空间;

    2.如果不是第一行,把模式空间追加到保持空间;

    3.如果是最后一行,把保持空间的内容替换到模式空间;

    4.通过-n,只输出模式空间最后一行的内容;

    通过这四步,最后一行就变成了  table=t1 name owner address   table=t2 id text col1 comment col5  table=t3 prod_name price,去掉 就完成了行的合并。

    参考代码如下:

    [root]$ cat sedMerge.txt
    table=t1
    name
    owner
    address
    table=t2
    id
    text
    col1
    comment
    col5
    table=t3
    prod_name
    price
    [root]$ cat sedMerge.txt | sed  -n '1h;1!H;$g;s/
    / /g;s/table/
    table/g;$p' | sed '/^$/d'
    table=t1 name owner address
    table=t2 id text col1 comment col5
    table=t3 prod_name price

    转载:sed之G、H、g、h使用 - fhefh - 博客园 (cnblogs.com)

    什么是sed?

    sed是面向流的行编辑器,所谓面向流,是指接受标准输入的输入,输出内容到标准输出上。

    sed如何处理数据?

    sed在正常情况下,将处理的行读入模式空间(pattern space),脚本中的“sed-command(sed命令)”就一条接着一条进行处理,知道脚本执行完毕。然后该行呗输出,模式(pattern space)被清空;接着,在重复执行刚才的动作,文件中的新的一行被读入,直到文件处理完毕。

    什么是Pattern Space,什么是Hold Space?

    pattern space相当于车间sed把流内容在这里处理。

    hold space相当于仓库,加工的半成品在这里临时储存。

    PS:你可以将pattern space看成是一个流水线,所有的动作都是在“流水线”上执行的;而hold space是一个“仓库”,“流水线”上的东东都可以放到这里。

    为什么要使用sed高级命令(G、H、g、h、n、N、x)?

    由于各种各样的原因,比如用户希望在某个条件下脚本中的某个命令被执行,或者希望模式空间得到保留以便下一次的处理,都有可能使得sed在处理文件的时候不按照正常的流程来进行。这个时候,sed设置了一些高级命令来满足用户的要求。

    sed命令:

    + g:[address[,address]]g 将hold space中的内容拷贝到pattern space中,原来pattern space里的内容清除

    + G:[address[,address]]G 将hold space中的内容append到pattern space 后

    + h:[address[,address]]h 将pattern space中的内容拷贝到hold space中,原来的hold space里的内容被清除

    + H:[address[,address]]H 将pattern space中的内容append到hold space 后

    + d:[address[,address]]d 删除pattern中的所有行,并读入下一新行到pattern中

    + D:[address[,address]]D 删除multiline pattern中的第一行,不读入下一行

    PS:不论是使用G、g还是H、h,它们都是将hold space里面的内容“copy”到pattern space中或者将pattern space中的内容“copy”到hold space中。

    附上英文的解释(注意其中的高亮单词):

    The "h" command copies the pattern buffer into the hold buffer. The pattern buffer is unchanged.

    Instead of exchanging the hold space with the pattern space, you can copy the hold space to the pattern space with the "g" command. This deletes the pattern space. If you want to append to the pattern space, use the "G" command. This adds a new line to the pattern space, and copies the hold space after the new line.

    示例:用sed模拟出tac的功能(倒序输出)。

    文件内容

    cat mm

    1
    2
    3

    解决方法:

     sed '1!G;h;$!d' mm 

    ps:1!G第1行不 执行“G”命令,从第2行开始执行。

           $!d,最后一行不删除(保留最后1行)

    图解分析过程

    P:Pattern Space

    H:Hold Space

    蓝色:Hold Space中的数据

    绿色:Pattern Space中的数据

    参考:

    《sed and awk 第二版》

    Sed - An Introduction and Tutorial by Bruce Barnett

    sed的高级应用 - haijd Article

    参考:【linux】sed之G、H、g、h使用_神奇的洋子-CSDN博客

    转载:sed n/N使用说明 - 生活费 - 博客园 (cnblogs.com)

    sed的语法格式:

    sed [option] {sed-command} {input-file}

    sed在正常情况下,将处理的行读入模式空间(pattern space),脚本中的“sed-command(sed命令)”就一条接着一条进行处理,知道脚本执行完毕。然后该行呗输出,模式(pattern space)被清空;接着,在重复执行刚才的动作,文件中的新的一行被读入,直到文件处理完毕。

    但是,由于种种原因,如用户希望在某个条件下,脚本中的某个命令被执行或希望模式空间(pattern space)保留,以便下一次使用,这都有可能使sed在处理文件的时候,不按照正常的流程来进行处理,这时候就需要用sed高级命令来满足需求。

    先来说说命令n和命令N

    命令n:读取下一行到pattern space。由于pattern space中有按照正常流程读取的内容,使用n命令后,pattern space中又有了一行,此时,pattern space中有2行内容,但是先读取的那一行不会被取代、覆盖或删除;当n命令后,还有其他命令p的时候,此时打印出的结果是n命令读取的那一行的内容。

    看下图,你就明白了。

    新建文件,其内容如下

    cat 1.txt

    1
    2

    正常sed流程

    使用n命令后,

    N命令:将下一行添加到pattern space中。将当前读入行和用N命令添加的下一行看成“一行”。

    新建文件1.txt

    cat 1.txt

    1
    2

    正常sed流程

    使用N命令后

    =========================================================

    2、sed选项
       -n    使用安静模式.则只有经过sed特殊处理的哪一行才会被列出来
       -e    传送带(前面执行完传递给后面)
       -f    跟随脚本文件名
       -r    脱意
       -i    直接修改读取文件

    3、sed命令详解
       a     新增, a 的后面可以接字串,而这些字串会在新的一行出现(目前的下一行)~
       c     取代, c 的后面可以接字串,这些字串可以取代 n1,n2 之间的行!
       d     删除,因为是删除啊,所以 d 后面通常不接任何咚咚;
       i      插入, i 的后面可以接字串,而这些字串会在新的一行出现(目前的上一行);
       p     列印,亦即将某个选择的资料印出。通常 p 会与参数 sed -n 一起运作~
       s     取代,通常这个 s 的动作可以搭配正规表示法!例如 1,20s/old/new/g 
       n    读取下一个输入行, 用下一个命令处理新的行

    4、以下是替换标记
      g    表示行内全面替换
      p    表示打印行
      w    表示把行写入一个文件
      x    表示互换模快板中的文本和缓冲区中的文本
      y    表示把一个字符翻译为另外的字符(不用于正则表达式)

    5、元字符集,匹配符
    ^       锚定行的开始. 如/^sed/ 匹配所有以sed开头的行
    $       锚定行的结束. 如/sed$/ 匹配所有以sed结尾的行
    .         匹配一个非换行符. 如/*sed/ 匹配s后接一个任意字符然后是d
    *        匹配零或多个字符. 如/*sed/ 匹配所有模块是一个或多个空格后紧跟sed的行
    []      匹配一个制定范围内的字符如. /[Ss]ed/ 匹配sed和Sed
    [^]    匹配一个不在制定范围内的字符. 如/[^A-RT-Z]ed/ 匹配不包含A-R和T-Z的一个字母开头,紧跟ed的行
    (..)        保存匹配的字符. 如s/(love)able/1rs loveable被替换成lovers
    &              保存搜索字符用来替换其它字符. 如s/love/**&**/ love这成**love**
    <             锚定单词的开始. 如/\> 锚定单词的结束. 如/love>匹配包含以love结尾的单词行
    x{m}       重复字符x,m次. 如/o{5}匹配包含5个o的行
    x{m,}      重复字符x,至少m次. 如 /o{5,}/匹配至少有5个o的行
    x{m,n}    重复字符x,至少m次.把多余n次. 如 /o{5,10}/匹配5-10个o的行

    6、sed中查找模式匹配
    .            单字通配符
    [0-9]      匹配0-9
    [^a-z]    不匹配a-z的所有其它字符
    “.*”         匹配””内任何字符串
    ^            匹配行开始
    $            匹配行结束

    7、例子
    删除: dd命令
    sed ‘2d’ file                 删除file文件的第2行
    sed ‘2,$d’ file             删除file文件的第2行到末尾所有行
    sed ‘$d’ file                删除file文件的最后一行
    sed ‘/test/’d file         删除file文件所有包含test的行
    sed d file                   删除file文件中的所有行
    sed 2,5d file              删除file中的2-5行
    sed /abc/d file          删除file中包含字符串abc所有的行

    替换: s命令
    sed ‘s/test/mytest/g’ file        在整行范围内把test替换为mytest. 如果没有g标记,则只有每行第一个匹配的test被替换成mytest
    sed -n ‘s/^test/mytest/p’ file        -n选项和p标志一起使用表示只打印那些发生替换的行, 如果某一行开头的test被替换成mytest,就打印它
    sed ‘s/^192.168.1.1/&localhost’ file    &符号表示替换字符串中被找到的部分. 所有以192.168.1.1开头的行都会被替换成它自己加localhost,变成192.168.1.1localhost
    sed -n ‘s/(love)able/1rs/p’ file    love被标记为1,所有loveable会被替换成lovers,而且替换的行会被打印出来
    sed ‘s#10#100#g’ file            不论什么字符,紧跟着s的命令都被认为是最新的分隔符,所以,’#’在这里是分隔符,代替了默认的”/”分隔符. 表示把所有10替换成100

    选定行的范围: 逗号
    sed -n ‘/test/,/check/p’ file        所有在模块test和check所确定范围内的行都被打印
    sed -n ‘5,/^test/p’ file                 打印从第5行开始到第一个包含以test开始行之间的所有行
    sed ‘/test/,/check/s/$/sed test/’ file    对于模块test和west之间的行,每行的末尾用字符串sed test替换

    多点编辑: e命令
    sed -e ‘1,5d’ -e ‘s/test/check/’ file    -e选项允许在同一行里执行多条命令.删除1-5行,check替换test
    sed -e ‘/and/s/aaa/bbb’ file           sed中用bbb替换同一行中包括字符串and的字符串aaa,而不是每一行中的字符串aaa

    读入文件: r命令
    sed ‘/test/r file_a’ file        file_a里的内容被读进来,显示在与test匹配的行后面. 如果匹配多行,则file_a内容将显示在所有匹配行的下面

    写入文件: w命令
    sed -n ‘test/w file_a’ file        file中所包含的test行都被写入file里

    插入: i命令
    sed ‘/test/i\ new line’ file        如果test被匹配, 则把反斜杠后面的文本插入到匹配行的上面
    sed -e ‘1 ia’ -e ‘$ a3′ file             在第一行上面插入a,在末尾行下面插入3

    下一个: n命令
    sed ‘/test/{n; s/aa/bb/;}; file        如果test被匹配, 则移动到匹配行的下一行,替换这一行的aa变为bb, 并打印该行,然后继续

    参考: sed命令_Linux sed命令:替换、删除、更新文件中的内容 (biancheng.net) Linux sed 命令 | 菜鸟教程 (runoob.com)

    sed从入门到深入的使用心得 - 骏马金龙 - 博客园 (cnblogs.com)

  • 相关阅读:
    傻瓜教程:asp.net(c#) 如何配置authentication,完成基于表单的身份验证
    ajax与php交互的get和post两种实现方式
    php 存储过程
    一万小时天才理论
    servlet阅读
    post and get
    合并两个有序数组(重新开始)
    Java参数传递问题
    一万小时(如何实现)阅读
    java IO 流的学习(我们到底能走多远系列1)
  • 原文地址:https://www.cnblogs.com/zhiminyu/p/14701474.html
Copyright © 2011-2022 走看看