2015-09-09 32 views
0

考虑这个输入文件。sed多行模式缓冲区刷新最后一行 - 正常行为?

# cat test.txt 
some other stuff 
some more other stuff 
first line 
second thingy 
third whatsit 
fourth oojiflop 
fifth item 
sixth widget 
this is the 
end of file 

运行这一个内胆就像我想要的一样工作(在OSX上创建了多个sed命令)。它删除“第一行”和“第五项”之间的所有行,但仅限于出现“第五项”时。

sed -e '/^first line/{' -e ':no' -e '$!{N' -e '/fifth item$/ b y' -e 'b no' -e ':y' -e 'd;};}' test.txt 

我担心的是,如果“第五项”模式不在行之后的“行头”被匹配,那么就不能打印到“第一线”之后的任何行。但它确实如此。它似乎在GNU风格以及BSD/OSX中起作用。

所以 - 如果用完

sed -e '/^first line/{' -e ':no' -e '$!{N' -e '/xxxxxxx$/ b y' -e 'b no' -e ':y' -e 'd;};}' test.txt 

然后,当它到达^第一线将开始填满使用“N”命令模式缓冲区。它会继续,寻找xxxxxxx,直到它击中EOF,并且$!测试失败。此时,执行从外括号中返回,并且在终止之前,sed似乎将整个模式缓冲区转储为标准输出。

我不知道这种行为 - 我的问题是,这是否是正常的行为,它是记录(事实上,当$测试失败全模式缓冲区得到倾倒!)

+2

您正在寻找的准确行为是什么? –

+0

'sed'默认打印模式空间,除非您使用'-n'。 –

+2

总会有一个点,在这'的sed -f script.sed'比上一行压扁一切成多个'-e'选择更明智。我认为你的脚本可能已经达到了这一点。 –

回答

0
sed -e '/^first line/{' -e ':no' -e '$!{N;/fifth item$/ b y' -e 'b no' -e ':y' -e 'd' -e '}' -e '}' test.txt 
  • 最后;};}不受SED,separe撑几个-e代替;理解,它应该在这种情况下
  • 我通过串连/fifth...与以往的表达降低您的版本。

另一种方式为OneLiner就像是在PROMT一次使用CTRL + V + J,而不是符/换行符的壳(不这样做,在vi它添加一个真正的新行)

0

你需要的,如果你达到最终的文件,删除所有多比赛,只要最后一行匹配或不是你的搜索表达式。

/^first line/ { 
    :no 
    $ { 
    d 
    } 
    $! { 
    N 
    /xxxxxxx$/ b y 
    b no 
    :y 
    d 
    } 
} 
+0

这可以被重构,以便:'/ ^第一行/ {:一个; $ d; N;/XXXXXXX $/d; BA}'如果你愿意更换';'由换行。问题的关键是,如果你检查结束文件,删除成功,然后下面如果没有档案结尾才会达成的任何命令。同样,匹配最终的字符串。 – potong