Linux sed - 需要帮助找出模式匹配不起作用的原因



以下sed行用于以下字符串。我的目标是将存储在value内部的数据放入一个变量中。

<input type="hidden" name="form_token" id="edit-system-site-maintenance-settings-form-token" value="0f5ae5a6e8bb84d3e18b30b7ff2a46b2" />
| sed 's/^.* value="//' 
| sed 's/ />//' 
| sed 's/"//'

但我真的认为最后一行是浪费。我不明白为什么当我试着在一行上做这件事时,它不匹配,如下所示。

| sed 's/" />//'

仅供参考,在第一个sed字符串处于以下状态之后

483deac360aa1d0ea89cedbdcc4d051e" />

一些迂腐的注释。不需要三重sed幂,您可以使用grep以及lookahead和lookbacking正则表达式来获得您想要的内容。

$> cat ./text 
<input type="hidden" name="form_token" id="edit-system-site-maintenance-settings-form-token" value="0f5ae5a6e8bb84d3e18b30b7ff2a46b2" />
$> grep -P -o "(?<=value=")([a-f0-9]*)(?=")" ./text 
0f5ae5a6e8bb84d3e18b30b7ff2a46b2

它在我的系统上运行良好,但你可能会逃脱:

sed -e 's?^.* value="??' -e 's?".*$??'

如这份成绩单所示:

pax> echo '<input type="hidden" name="form_token" id="edit-system-site-maintenance-settings-form-token" value="0f5ae5a6e8bb84d3e18b30b7ff2a46b2" />' | sed -e 's?^.* value="??' -e 's?".*$??'
0f5ae5a6e8bb84d3e18b30b7ff2a46b2

GNU sed可以使用其他分隔符,这可以最大限度地减少sed命令(如/////)中经常出现的Z字形。

此外,您只需要调用sed一个副本,并为其提供在每行上运行的多个命令。

第二个命令应该足以去除超过该值的所有内容,尤其是在更复杂的情况下,如:

<input type="hidden" name="xyzzy" value="plugh" something="else" />

如果希望使用像sed这样的文本处理工具来处理XML。使用适当的工具有更多"可靠"的方法可以做到这一点,但我假设您可以将XML格式控制到sed可以处理的程度。

这可能对您有用:

a='<input type="hidden" name="form_token" id="edit-system-site-maintenance-settings-form-token" value="0f5ae5a6e8bb84d3e18b30b7ff2a46b2" />'
b=$(sed 's/.*value="("[^"]*).*/1/' <<<$a)
echo $b
0f5ae5a6e8bb84d3e18b30b7ff2a46b2

说明:

  • 将输入字符串保存到变量a
  • 将命令替换的结果分配给变量b
    • 使用here字符串将输入字符串传递到sed <<<$a
    • 用反引用1替换整个输入字符串,该反引用包含值value的双引号之间的所有内容

最新更新