使用 grep/sed/awk 从字符串中提取单词

使用 grep/sed/awk 从字符串中提取单词

我有一个字符串

00:28:04 /usr/lib/jvm/jre/bin/java -DJDBC_CONNECTION_STRING= -Dspring.profiles.active=qa -XX:MaxPermSize=256

并想要提取qa后面的单词-Dspring.profiles.active

我将字符串保存在文件 text.txt 中只是为了对其进行演示。

当我做

grep -r -o "spring.profiles.active=" text.txt

结果是spring.profiles.active=

这个词并不总是qa,它可能是proddev

我想做的是找到这个词spring.profiles.active提取=那个词。

我想编写这个脚本,因为我使用单词配置服务器上的其他项目。

这可能吗?如果可以,我该怎么做?

答案1

您可以grep与 PCRE ( -P) 一起使用:

grep -Po 'spring.profiles.active=\K[^ ]+' <<<'.....string.....'
  • spring.profiles.active=将逐字匹配此子字符串,\K将丢弃匹配

  • [^ ]+将选择所需的部分,即之后的部分spring.profiles.active=,直到下一个空格

对于文件:

grep -Po 'spring.profiles.active=\K[^ ]+' file.txt

例子:

% grep -Po 'spring.profiles.active=\K[^ ]+' <<<'00:28:04 /usr/lib/jvm/jre/bin/java -DJDBC_CONNECTION_STRING= -Dspring.profiles.active=qa -XX:MaxPermSize=256'
qa

sed采取类似的逻辑:

sed -r 's/.*spring.profiles.active=([^ ]+).*/\1/' <<<'.....string.....'

例子:

% sed -r 's/.*spring.profiles.active=([^ ]+).*/\1/' <<<'00:28:04 /usr/lib/jvm/jre/bin/java -DJDBC_CONNECTION_STRING= -Dspring.profiles.active=qa -XX:MaxPermSize=256'
qa

处理错误:

在脚本中,您可能需要处理没有匹配的情况,换句话说,原始字符串不包含spring.profiles.active=。在上面的sed例子中,您获得了整个原始字符串,这可能会产生问题:

% var="$(sed -r 's/.*spring.profiles.active=([^ ]+).*/\1/' <<<'00:28:04 /usr/lib/jvm/jre/bin/java -DJDBC_CONNECTION_STRING= -XX:MaxPermSize=256')"
% echo $var
00:28:04 /usr/lib/jvm/jre/bin/java -DJDBC_CONNECTION_STRING= -XX:MaxPermSize=256

如果您希望在没有匹配时获取空字符串,请将选项添加到命令-nsed,并将p选项添加到sed s命令中,如下所示:

% var="$(sed -rn 's/.*spring.profiles.active=([^ ]+).*/\1/p' <<<'00:28:04 /usr/lib/jvm/jre/bin/java -DJDBC_CONNECTION_STRING= -XX:MaxPermSize=256')"
% echo $var

% var="$(sed -rn 's/.*spring.profiles.active=([^ ]+).*/\1/p' <<<'00:28:04 /usr/lib/jvm/jre/bin/java -DJDBC_CONNECTION_STRING= -Dspring.profiles.active=qa -XX:MaxPermSize=256')"
% echo $var
qa

然后您可以测试 $var 是否为空。

答案2

使用awk

awk -F"-Dspring.profiles.active=" '{sub(/ .*/,"",$2);print $2}' <<<'your_string'

或者

awk -F"-Dspring.profiles.active=" '{sub(/ .*/,"",$2);print $2}' your_file

例子

% awk -F"-Dspring.profiles.active=" '{sub(/ .*/,"",$2);print $2}' <<<'00:28:04 /usr/lib/jvm/jre/bin/java -DJDBC_CONNECTION_STRING= -Dspring.profiles.active=qa -XX:MaxPermSize=256'
qa

答案3

我将把 Perl 放进去:

<<<'string' perl -lane '$F[3]=~s/.*?=//;print($F[3])'
  • -l: 启用自动行结束处理。它有两个不同的效果。首先,当与 -n 或 -p 一起使用时,它会自动剪切 $/(输入记录分隔符)。其次,它为 $\(输出记录分隔符)分配 octnum 的值,以便任何打印语句都会重新添加该分隔符。如果省略 octnum,则将 $\ 设置为 $/ 的当前值。
  • -a:与 -n 或 -p 一起使用时打开自动拆分模式。对 @F 数组的隐式拆分命令是 -n 或 -p 生成的隐式 while 循环中的第一件事。
  • n:导致 Perl 假设您的程序周围有以下循环,这使得它像 sed -n 或 awk 一样迭代文件名参数:

    LINE:
      while (<>) {
          ...             # your program goes here
      }
    
  • -e:可用于输入一行程序。
% <<<'00:28:04 /usr/lib/jvm/jre/bin/java -DJDBC_CONNECTION_STRING= -Dspring.profiles.active=qa -XX:MaxPermSize=256' perl -lane '$F[3]=~s/.*?=//;print($F[3])'
qa

相关内容