使用grep从键值对列表中提取值

时间:2018-06-28 15:53:04

标签: regex grep regex-lookarounds

我有一个包含键值对列表的字符串,例如:“ a:1,b:2,c:3”。我想提取指定键的值,例如我将为“ a”得到“ 1”。我打算用这样的正则表达式来做到这一点:

'(?<=(^|,)$KEY:)^,*'

,但是grep似乎不支持环视。 (我什至不确定此正则表达式是否正常工作。)还有另一种方法吗?

3 个答案:

答案 0 :(得分:2)

保持简单。您不需要所有这些看起来很简单的东西,只需对所需字段进行简单的字符串比较,然后使用awk打印您想要的其他字段:

$ awk -v key="a" -v RS=',' -F':' '$1==key{print $2}' <<< "a:1,b:2,c:3,"
1

该awk脚本可与任何UNIX盒上任何shell中的任何awk一起使用。如何将字符串传递给awk将取决于shell,<<<是一种bash行为,但是您可以改用以下方式:

$ echo "a:1,b:2,c:3," | awk -v key="a" -v RS=',' -F':' '$1==key{print $2}'
1

或执行其他操作,具体取决于您要解析的字符串是存储在变量还是文件中,或者...。

答案 1 :(得分:1)

您可以将read与带有冒号和逗号的IFS用作字段分隔符,如下所示:

IFS=':,' read -ra arr <<< "a:1,b:2,c:3"

这将为您提供以下数组:

declare -p arr
declare -a arr=([0]="a" [1]="1" [2]="b" [3]="2" [4]="c" [5]="3")

如果要列出键值对,请使用:

for ((i=0; i<${#arr[@]}; i+=2)); do echo "${arr[i]} => ${arr[i+1]}"; done

a => 1
b => 2
c => 3

要能够获取给定键的单个值,可以使用以下sed

k=a; sed -E "s/(^|.*,)$k:([^,]*).*/\2/" <<< "a:1,b:2,c:3"
1

k=b; sed -E "s/(^|.*,)$k:([^,]*).*/\2/" <<< "a:1,b:2,c:3"
2

k=c; sed -E "s/(^|.*,)$k:([^,]*).*/\2/" <<< "a:1,b:2,c:3"
3

答案 2 :(得分:1)

您可以使用

grep -oP "(?:^|,)$KEY:\K[^,]+"

-o选项输出匹配项。 -P启用PCRE引擎。字符串插值必须使用双引号,以便可以对$KEY进行插值。

模式匹配:

  • (?:^|,)-字符串或逗号开头
  • $KEY-KEY变量
  • :-冒号
  • \K-匹配重置运算符,该运算符将舍弃到目前为止匹配的整个文本
  • [^,]+-除,以外的1个以上的字符