sed:只有当其中一行匹配第三个字或任何模式时,才在两个字之间打印行

我知道sed使用下面的命令从test.txt打印单词FOO和BAR之间的行

sed -n '/FOO/,/BAR/p' test.txt 

但是如何使sed打印FOO和BAR之间的行,只有当其中一行具有匹配的模式时才行

例如,文件text.txt有以下几行:

 Error- Undefined port line1 line2 Undefined port in ALU1 line3 Error- Undefined port line4 line5 Undefined port in LSU line6 Error- Undefined port line7 line8 Undefined port in FGU line9 Error- Undefined port line10 line11 Undefined port in ALU2 line12 

我想打印出两个连续出现的单词“错误”之间的行,只有当其中一行包含单词“ALU”。

所以我只想打印出下面的错误信息:

 Error- Undefined port line1 line2 Undefined port in ALU1 line3 Error- Undefined port line10 line11 Undefined port in ALU2 line12 

Solutions Collecting From Web of "sed:只有当其中一行匹配第三个字或任何模式时,才在两个字之间打印行"

为了达到这个目的,你需要在sed脚本和保持缓冲区中分支。

该脚本使用两个缓冲区:模式缓冲区(它是sed存储当前正在处理的行,用于模式匹配测试的缓冲区)和保持缓冲区(缓冲区用于存储以前的行)。 我们的想法是存储最后一个/Error/模式匹配的所有行,并在下一个/Error/匹配或流结束时检查/ALU/发生。

 sed -n ' # if /Error/ pattern occured, jump to /ALU/ check /Error/ b alu_check # else append current line to the hold buffer H # if the current line is the last one, jump to /ALU/ check $ b alu_check # otherwise jump to end of script (= finish processing of this line) b # alu_check: :alu_check # exchange current pattern buffer with hols buffer context x # print previous record if /ALU/ occured /ALU/ p ' 

x顺序交换模式缓冲区上下文(当前行)与保持缓冲区上下文(从上次记忆) – 注意,它存储当前行/错误/模式到下一次保持缓冲区的行

H将当前行上下文附加到保留缓冲区

awk变体:

  awk 'BEGIN{RS=ORS="\n\n";FS="\n"}/^Error.+ALU/' file 

RS (记录分隔符)强制在空行上

FS (字段分隔符)在单行返回

ORS (输出记录分隔符)被设置在输出的空白行上(如果你不需要,就删除它)

/^Error.+ALU/如果记录(文本块)以Error开始并包含ALU – >打印块。

awk -v RS = -v ORS =“\ n \ n”'/ ALU /'文件

遗产:

 awk '{FS="\n";RS=""} $0 ~ /ALU/ {print $0"\n"}' file