awk和多行匹配(子正则表达式)
我正在尝试使用awk解析多行表达式。其中一个看起来像这样:awk和多行匹配(子正则表达式),awk,Awk,我正在尝试使用awk解析多行表达式。其中一个看起来像这样: _begin hello world ! _attrib0 123 _attrib1 super duper _attrib1 yet another value _attrib2 foo _end 我需要提取与_begin和_attrib1关联的值。因此,在本例中,awk脚本应返回(每行一个): 使用的分隔符是制表符(\t)字符。空格仅在字符串中使用。以下awk脚本执行此任务: #!/usr/bin/awk
_begin hello world !
_attrib0 123
_attrib1 super duper
_attrib1 yet another value
_attrib2 foo
_end
我需要提取与_begin和_attrib1关联的值。因此,在本例中,awk脚本应返回(每行一个):
使用的分隔符是制表符(\t)字符。空格仅在字符串中使用。以下awk脚本执行此任务:
#!/usr/bin/awk -f
BEGIN { FS="\t"; }
/^_begin/ { output=$2; }
$1=="_attrib1" { output=output " " $2; }
/^_end/ { print output; }
您没有指定是否希望选项卡(\t
)作为输出字段分隔符。如果有,请告诉我,我会更新答案。(或者你可以;这很琐碎。)
当然,如果你想要一个可怕的替代方案(因为我们快到万圣节了),这里有一个使用sed
的解决方案:
$ sed -ne '/^_begin./{s///;h;};/^_attrib1[^0-9]/{s///;H;x;s/\n/ /;x;};/^_end/{;g;p;}' input.txt
hello world ! super duper yet another value
这是怎么回事?姆瓦哈哈,很高兴你问我
- 开始代码>--当我们看到
时,将其剥离并将行的其余部分存储到sed的“hold buffer”中\u begin
/^属性1[^0-9]/{s//;H;x;s//\n//;x;}代码>--当我们看到
时,将其剥离,附加到保留缓冲区,交换保留缓冲区和模式空间,用空格替换换行,然后再次交换保留缓冲区和模式空间\u attrib1
--我们已经到了末尾,所以将保持缓冲区拉入模式空间并打印它/^\u end/{;g;p;}
#!/bin/bash
awk 'BEGIN {FS="\t"} {if ($1=="_begin" || $1=="_attrib1") { output=output " " $2 }} END{print output}'
_attrib11正在使此脚本失败(_attrib1匹配)。您提供的示例数据中没有
_attrib11
。如果愿意,您可以使用$1==“\u attrib1”
等条件来处理该问题,而不是/^\u attrib1/
,或者您可以将其保留为正则表达式,但终止它,如$1~/^\u attrib1$/
。我推荐第一种替代方案;始终先选择字符串匹配,再选择正则表达式(至少)。根据您的新要求更新我的答案。为了您的阅读乐趣,还添加了一个sed
备选方案。@ghoti,您的第一个示例对我不适用。只打印空行。为什么?@Tedee12345-可能与您的输入数据有关。为什么不,我们看看能做些什么?
#!/bin/bash
awk 'BEGIN {FS="\t"} {if ($1=="_begin" || $1=="_attrib1") { output=output " " $2 }} END{print output}'