我正在尝试提取看起来像这样的块注释:
<tag_1:sub_tag>
This is 1 comment.
</tag_1:sub_tag>
或
<any_tag>
This is yet another comment.
</any_tag>
通过
find . -type f -exec awk '/<variable>/,/<\/variable>/{print FILENAME ":" FNR ":" $0}' {} \;
但我不确定如何让$ variable接受使用外卡*
之类的内容。有办法吗?
这必须在子文件夹上递归完成。
答案 0 :(得分:1)
永远不要使用范围表达式,因为它们只是最简单的工作,但是当问题变得更加有趣时,需要完全重写和/或重复条件。始终使用标志,例如src/main/java
。
在这种情况下,假设您的输入文件与您提供的示例一样简单且格式良好,因此您不需要XML解析器:
awk '/start/{f=1} f; /end/{f=0}'
只需将其粘贴在awk -v OFS=':' '
match($0,/^<[^\/>]+>$/) {
f = 1
end = "</"substr($0,RSTART+1,RLENGTH-1)
}
f {print FILENAME, FNR, $0}
$0 == end { f = 0 }
' file
file:1:<tag_1>
file:2:This is 1 comment.
file:3:</tag_1>
file:7:<any_tag>
file:8:This is yet another comment.
file:9:</any_tag>
命令中,如果您觉得有用,请随意将其全部塞进一行。
如果要更改分隔标记行中的一个或两个是否只是更改设置/清除标记find
的位置,例如:
f
因为你似乎对如何运行它感到困惑:
awk -v OFS=':' '
$0 == end { f = 0 }
f {print FILENAME, FNR, $0}
match($0,/^<[^\/>]+>$/) {
f = 1
end = "</"substr($0,RSTART+1,RLENGTH-1)
}
' file
file:2:This is 1 comment.
file:8:This is yet another comment.
$ cat file
<tag_1:sub_tag>
This is 1 comment.
</tag_1:sub_tag>
or
<any_tag>
This is yet another comment.
</any_tag>
$ awk -v OFS=':' '
$0 == end { f = 0 }
f {print FILENAME, FNR, $0}
match($0,/^<[^\/>]+>$/) {
f = 1
end = "</"substr($0,RSTART+1,RLENGTH-1)
}
' file
file:2:This is 1 comment.
file:8:This is yet another comment.
是我的提示。有问题吗?
我仍然不确定你为什么遇到问题,但这有帮助:
$
$ ls
file
$ cat file
<tag_1:sub_tag>
This is 1 comment.
</tag_1:sub_tag>
or
<any_tag>
This is yet another comment.
</any_tag>
$ find . -type f -exec awk -v OFS=':' '
$0 == end { f = 0 }
f {print FILENAME, FNR, $0}
match($0,/^<[^\/>]+>$/) {
f = 1
end = "</"substr($0,RSTART+1,RLENGTH-1)
}
' {} \;
./file:2:This is 1 comment.
./file:8:This is yet another comment.
$ find . -type f -exec awk -v OFS=':' '$0 == end { f = 0 } f {print FILENAME, FNR, $0} match($0,/^<[^\/>]+>$/) { f = 1; end = "</"substr($0,RSTART+1,RLENGTH-1) }' {} \;
./file:2:This is 1 comment.
./file:8:This is yet another comment.
答案 1 :(得分:0)
要求救援!
awk '/<tag_1>/,/<\/tag_1>/' file
如果要将标记名称作为变量传递,可以将其更改为
awk -v tag="tag_1" '$0~"<"tag">",$0~"</"tag">"' file
这将在任何打开和关闭的标签之间打印值
awk '/<[^/>].*>/{s=1;next} /<\/[^>].*>/{s=0} s' file
然而,不检查它们是否匹配。
我确信它可以进一步简化,但这样可以确保打开和关闭的代码匹配(仍然无法处理嵌套代码)
$ awk '/<[^/>].*>/{sub("<","</");t=$0;delete a;c=0;s=1;next}
t==$0{for(i=1;i<=c;i++)print a[i];delete a;c=s=0;t=""}
s{a[++c]=$0}' file
在开放标记之后缓冲行,直到找到匹配的关闭标记,然后打印缓冲的行,重置等。