Regex gawk-提取文本并将其放在同一行上

Regex gawk-提取文本并将其放在同一行上,regex,parsing,awk,gawk,Regex,Parsing,Awk,Gawk,好的,我有一些文字: === Blah 1 === ::Junk I wish: 2 Ignore <br/> ::More Junk: 1.2-2.7 <br/> ::ABC: [http://www.google.com (STUFF/I/Want)]<br/> ::More2: Ignore<br/> ::More Stuf 2 Ignore: N/A<br/> === Blah 2 === ::Junk I wish: Mor

好的,我有一些文字:

=== Blah 1 ===
::Junk I wish: 2 Ignore <br/>
::More Junk: 1.2-2.7 <br/>
::ABC: [http://www.google.com (STUFF/I/Want)]<br/>
::More2: Ignore<br/>
::More Stuf 2 Ignore: N/A<br/>

=== Blah 2 ===
::Junk I wish: More 2 Ignore <br/>
::More Junk: 1.2-2.7 <br/>
::ABC: [http://www.google.com (Other/STUFF/I/Want)]<br/>
::More2: More Ignore<br/>
::More Stuf 2 Ignore: More N/A<br/>
我已经想出了如何抓住我想要的部分线路:

gawk  '/===/ {print } /ABC/ {print $3}' file_name
这将产生以下结果:

=== Blah 1 ===
(STUFF/I/Want)]<br/>
=== Blah 2 ===
(Other/STUFF/I/Want)]<br/>
==Blah 1===
(填充/我/想要)
无稽之谈=== (其他/材料/我/想要)

我不明白的是如何去掉我不想要的其他字符,并将其放在一行。

使用
printf
而不是
print
忽略换行符,只打印第一个块中的第二个和第三个字段,并使用
sub
丢弃第二个块中不想要的内容:

awk '/===/{printf "%s %s, ",$2,$3}/ABC/{sub(/].*/,"");print $3}' file
Blah 1, (STUFF/I/Want)
Blah 2, (Other/STUFF/I/Want)
如果标题长度可变:

awk '/===/{gsub(/ ?=+ ?/,"");printf "%s, ",$0}/ABC/{sub(/].*/,"");print $3}' file
Blah 1, (STUFF/I/Want)
Blah 2, (Other/STUFF/I/Want)
gawk'/===/{header=gensub(“*==*”,“,”g“,$0)}/ABC/{ABC=gensub(“]
,”,“,”g“,$3);打印页眉,“ABC}”文件名
这可能对你有用。它将剥离的信息保存到变量中,然后打印它们。

单向

script.awk的内容

BEGIN {
    ## Characters to separate output fields
    OFS = ", "
}

## When line begins with several equal signs, remove them, both leading
## and trailing, and save the title.
$1 ~ /^=+$/ {
    gsub( /\s*=\s*/, "", $0 )
    title = $0
    next
}

## For the second field, split line with both pair of parentheses and 
## print second field.
$1 ~ /ABC/ {

    ## For GNU-Awk
    #split( $0, abc_line, /(\()|(\))/, seps )
    #printf "%s%s%s%s%s\n", title, OFS, seps[1], abc_line[2], seps[2]

    ## For Awk
    split( $0, abc_line, /(\()|(\))/ )
    printf "%s%s(%s)\n", title, OFS, abc_line[2]

}
像这样运行:

awk -f script.awk infile
它产生:

Blah 1, (STUFF/I/Want)
Blah 2, (Other/STUFF/I/Want)

有时在awk中,如果您寻找一个非正统的记录分隔符,解决方案会变得非常简单:

awk -v RS=' *=== *|[()]' '
  NR%4==2 {printf "%s, ", $0}
  NR%4==0 {print "(" $0 ")"}
'

这里,一个记录分隔符是
====
,可以选择用空格或左括号或右括号括起来。

为什么不在第一个块中使用
/=={header=$2”“$3}
,而在第二个
gensub(“]
,“,”g“,$3)”我在1分钟内输入了它,没有想太多。你的解决方案也是对的。谢谢你对你的代码的清晰解释,诗句只是给了我一个答案。我希望在这里学习,所以非常感谢。你知道为什么有人告诉我split只接受3个参数吗?为什么不直接使用
title=$2“$3
?@Doug:恐怕4参数
split
函数来自
GNU awk
。我也编辑了脚本以使用普通的
awk
。@sudo\u O:以防万一标题超过2个字。有趣的是,我使用的是Gnu awk,但它是一个连接到Windows的端口。也许它背后有几个版本。修改后的代码运行良好。谢谢大家!!谢谢,这正是我想要的,非常简洁。没问题,你很接近。坚持下去,awk非常强大。
Blah 1, (STUFF/I/Want)
Blah 2, (Other/STUFF/I/Want)
awk -v RS=' *=== *|[()]' '
  NR%4==2 {printf "%s, ", $0}
  NR%4==0 {print "(" $0 ")"}
'