可以在 ${var//OLD/NEW} 替换中使用 OR 表达式吗?

Can OR expressions be used in ${var//OLD/NEW} replacements?

我在 bash 脚本中测试了一些字符串操作,我很快意识到它不理解正则表达式(至少不理解我用于字符串操作的语法),然后我尝试了一些 glob 表达式,它似乎能理解其中的一些,有些则不能。具体来说:

FINAL_STRING=${FINAL_STRING//<title>/$(get_title)}

是我尝试使用的主要操作,上面的行有效,将 $FINAL_STRING 上出现的所有 <title> 替换为 $(get_title)... 和

local field=${1/#*:::/}

有效,分配 </code> 从开始到第一次出现 <code>::: 的所有内容都没有替换(删除)。但是 # 做我希望 ^ 做的事情。 Plus 当我在这里尝试使用 {,,} glob 表达式时:

FINAL_STRING=${FINAL_STRING//{<suffix>,<extension>}/${SUFFIX}}

${SUFFIX} 替换任何 <suffix> OR <extension> ,它不起作用。

所以我看到它不采用正则表达式,也不采用 glob 模式...那么它需要什么?是否有关于 symbols/expressions 被普通 bash 字符串操作(特别是子字符串替换)所理解的内容的详尽清单?或者 *?###%%% 是唯一有效的东西吗?

(我试图仅依靠 plain bash,而不调用 sedgrep做我想做的)

详细信息可以在 bash 手册的 Shell Expansions 部分中找到。完整的画面复杂得惊人。

Shell Parameter Expansion 部分描述了您正在做的事情。您会看到

中的模式
${parameter/pattern/string}

使用 Filename Expansion rules, and those don't include Brace Expansion - 这是在处理命令行参数时较早完成的。文件名扩展 "only" 进行 ?*[...] 匹配(除非设置了 extglob)。

但是参数扩展不仅仅是文件名扩展,尤其是您在 #%.

中注意到的锚定

bash 实际上处理正则表达式;具体来说,[[ =~ ]] 运算符,然后您可以使用魔术变量 $BASH_REMATCH 将其分配给变量。这很时髦,但很管用。

参见:http://www.linuxjournal.com/content/bash-regular-expressions

请注意,这是 bash 独有的 hack 功能。

除了 bash 之外,对于在 shell 中工作的代码,做这种事情的老派方法确实是使用 #/##/% /%% 以及围绕 case 语句的循环(支持基本的 * glob 匹配)。