使用Sed / awk / grep或任何其他工具在Linux environemnt中提取子字符串

时间:2018-02-12 04:13:28

标签: regex linux awk sed grep

我只想从特定的字符串中获取子字符串。

例如,我有"sec(name=test)"字符串。而且,我想使用shell提取name=test字符串。

我尝试过以下命令来提取"name=test"值。但是,我的结果为sec()

echo "sec(name=test)"| grep -P '(sec\((.*)\))'

你能帮忙解决一下吗?

3 个答案:

答案 0 :(得分:1)

你很接近,但除非你想egrep(可能有或没有),sed有基本正则表达式,例如

$ echo "sec(name=test)"| sed 's/^[^(]*(\([^)]*\)).*$/\1/'
name=test

标准替换命令的详细信息为s/find/replace/,其中find部分有点收集反向引用的设置,以便在replace部分使用命令。例如,

find部分

  1. ^ - 在字符串开头
  2. 开始匹配的锚点
  3. [^(]* - 匹配[..class..]中的所有字符"^("(不是开场白)
  4. ( - 消耗开场白
  5. \(...\)收集字符以保存为反向引用,这些字符为"[^)]*所有内容都不是结束语,
  6. ) - 消耗闭幕式,
  7. .*$ - 其余部分。
  8. replace部分

    1. \1插入保存为第一个反向引用的字符(\(...\)之间的内容name=test
    2. 而且,你已经完成了......

答案 1 :(得分:0)

使用Gnu-Sed,你也可以写

 echo "sec(name=test)"| sed -r 's/sec\(([^)]*)\)/\1/'

使用sed -r,当用于分组时,你的圆形parens不需要被屏蔽,但是当字面意思时。有关详细信息,请参阅 man sed

这会查找秒数(然后是任意数量的字符,不是关闭的数据,而是关闭的数据。

答案 2 :(得分:0)

grep将打印匹配的行,或者-o匹配的字符串。捕捉括号本身并没有做任何改变这一点。

grep -P有一种方法可以说"匹配括号内的东西,但只有当以下的外观也符合"所以你可以做到

echo "sec(name=test)"| grep -oP '(?<=sec\().*?(?=\))'

后瞻(?<=sec\()表示匹配必须紧跟sec(,前瞻(?=\))同样要求匹配后跟)。我将匹配表达式从贪婪的.*更改为吝啬的.*?,以避免它跨越一组括号。当然,这可能不是你想要的;你的问题没有揭示我们应该期望匹配的文本(特别是,它可以包含嵌套的括号吗?)

但这很复杂;更简单和便携的解决方案是使用sed替换所需字符串之前和之后的内容,然后打印。

echo "sec(name=test)"| sed -n 's/.*sec\(([^()]*)\).*/\1/p'

请注意sed使用的正则表达式方法比grep -P支持的正则方言更简单,特别是,未加引号的括号()按字面意思匹配,而反斜杠的方言则用于分组 - 与他们在Perl中的工作方式相反,例如egrep