在两个常量字符串之间提取WORD



我有以下字符串

xml_srx_name="<name>SRX-NAME</name>"

我正在尝试打印>和& lt;所以它会输出SRX-NAME

我真的很接近,但这是我得到的:>SRX-NAME<</strong>这就是我用这个命令所能达到的效果:

$ cat $xml_srx_name | awk '/SRX-NAME/ {print $1}' | grep -oPz "(?s)>.*?<" | tr '' 'n'
Output:
>SRX-NAME<

如果您最终使用了一个使用cat,awk,greptr的复合命令,那么您可能有一个很好的反模式示例。仅awk就足够了:

$ xml_srx_name="<name>SRX-NAME</name>"
$ awk -F'<|>' '/SRX-NAME/ {print $3}' <<< "$xml_srx_name"
SRX-NAME

或与sed:

$ sed '/SRX-NAME/s/.*>(.*)<.*/1/' <<< "$xml_srx_name"
SRX-NAME

您也可以只使用grep -oP使用perl兼容的regex:

<(name>)K[^<]+(?=</1)

或者写出完整的模式:

<name>K[^<]+(?=</name>)

  • <Match literal
  • (name>)K捕获组1中的name>
  • [^<]+匹配<以外的1+字符
  • (?=</1)正向向前看,向右断言

例子

xml_srx_name="<name>SRX-NAME</name>"
grep -oP "<(name>)K[^<]+(?=</1)" <<< "$xml_srx_name"

输出
SRX-NAME

bash演示


或者使用sed和一个捕获组:

xml_srx_name="<name>SRX-NAME</name>"
sed 's/.*<name>([^<]+)</name>.*/1/' <<< "$xml_srx_name"

sed演示

input="test<hello>text"
rightpart=${input#*<}   # remove prefix up to "<" (included)
output=${rightpart%>*}  # remove suffix from ">" (included)
echo $output

在bash中使用extglob,您可以一步完成:

shopt -s extglob
input='test<hello>heythere'
echo "${input//@(*<|>*)/}"

这里@(<|>)匹配子字符串从start到

你可以试试

  1. 在末尾添加| tr -d '<>'
  2. 使用cat … |grep -o SRX-NAME
  3. 使用cat … |cut -d > -f 2 | cut -d < -f 1

您可以使用零长度断言的GNUgrep,如下所示让file.txt的内容为

xml_srx_name="<name>SRX-NAME</name>"

然后

grep -Po "(?<=>).*(?=<)" file.txt

输出
SRX-NAME

解释:在>之后和<之前找到0个或更多的字符。

(在GNU grep 3.4中测试)

在任何Unix系统的任何shell中使用任何sed或awk:

$ xml_srx_name="<name>SRX-NAME</name>"
$ echo "$xml_srx_name" | awk -F'[<>]' '{print $3}'
SRX-NAME
$ echo "$xml_srx_name" | sed 's/.*>(.*)<.*/1/'
SRX-NAME

任何包含SRX-NAME的脚本都是毫无意义的,因为它意味着你已经知道你想要找到的字符串,所以可以只做echo 'SRX-NAME'

最新更新