我必须以相反的顺序搜索特定的字符串并打印它。
在下面的例子中,我想从模式搜索not in order
直到模式number of
。
例如:输入文件包含:
number of characters a[1]
reg1
reg2
reg3
info a[1] is not in order
number of characters a[3]
reg1
reg2
reg3
info a[3] is in order
number of characters a[2]
reg1
reg2
reg3
info a[2] is not in order
输出应该是:
number of characters a[1]
reg1
reg2
reg3
info a[1] is not in order
number of characters a[2]
reg1
reg2
reg3
info a[2] is not in order
答案1
使用in order
换行符作为段落分隔符,我们可以执行以下操作:
awk -v RS='in order\n' '/not/{print $0 "in order"}'
awk
将由 (记录分隔符) 中的模式分隔的文本RS
视为记录,并且每个操作都针对一条记录执行。因此,/not/
测试记录是否匹配not
,然后我们将记录($0
)与 awk 删除的分隔符文本一起打印。
所以:
$ mawk -v RS='in order\n' '/not/{print $0 "in order"}' foo
number of characters a[1]
reg1
reg2
reg3
info a[1] is not in order
number of characters a[2]
reg1
reg2
reg3
info a[2] is not in order
答案2
如果块必须以包含is in order
或 的行结束is not in order
,我们可以删除它们之间的内容......
$ sed '/is not in order/,/is in order/ {/is not in order/n;d}' file
number of characters a[1]
reg1
reg2
reg3
info a[1] is not in order
number of characters a[2]
reg1
reg2
reg3
info a[2] is not in order
笔记:
/is not in order/,/is in order/
is not in order
找出和之间的界线is in order
(含){some commands}
将这些命令分组/is not in order/n
从下一个命令开始跳过具有此模式的行d
删除指定行
找到这一行然后再次找到它来跳过它似乎很复杂,但我们不能用空行来代替,否则sed
会打开它的在这里操作在下一个空行处标记并继续直到下一个is in order
,这将删除过多。
答案3
另一种方法:
tac file | awk ' BEGIN {weprint=0 ; rem="not necessary, but for clarity"}
/is not in order$/ { weprint=1 ;}
( weprint == 1) { print $0 ; rem="same remark here..."; }
/^number of/ { weprint=0 ;}
' | tac
如果需要的话可以缩短...
如果您想要分隔线:将最后一行更改为
"/^number of/" { print ; weprint=0;}
答案4
perl -00 -ne 'print if /not in order/' file
该-00
选项按段落读取文件。在文件的所有段落上添加一个隐式循环。
然后 ,如果段落包含所需的“无序”文本,则打印该段落。-n