如何根据Bash版本/功能编写条件代码?

时间:2015-08-12 08:14:17

标签: regex bash msysgit

我在我的一个Bash脚本中使用=~。但是,我需要使脚本与不支持该运算符的Bash版本兼容,特别是与msysgit not build against libregex一起提供的Bash版本。我有一个使用expr match的变通方法,但由于某种原因,它再次无法在Mac OS X上运行。

因此,我想仅使用expr match if [ -n "$MSYSTEM" -a ${BASH_VERSINFO[0]} -lt 4 ],否则使用=~。问题是Bash似乎总是解析整个脚本,即使msysgit Bash会在运行时执行解决方法,它在解析脚本时仍会遇到=~

是否可以根据Bash版本在同一脚本中有条件地执行代码,或者我应该采用另一种方式来解决此问题?

3 个答案:

答案 0 :(得分:2)

在您的情况下,您可以使用等效模式匹配替换正则表达式。

[[ $foo = \[+([0-9])\][[:space:]]* ]]

一些解释:

  • 模式与整个字符串匹配。以下正则表达式和模式是等效的:

    1. ^foo$foo
    2. ^foofoo*
    3. foo$*foo
    4. foo*foo*
  • +(...)匹配所包含模式的一个或多个匹配项,在本例中为[0-9]。也就是说,如果$pattern$regex匹配相同的字符串,那么+($pattern)($regex)+也是如此。

答案 1 :(得分:1)

我目前的解决方案是在所有平台上使用grep -q。这可以避免任何条件或复杂的代码构造。

可能只是在运行时使用eval来解析包含=~的代码也会起作用,但是这会使代码更难以阅读。

答案 2 :(得分:0)

对于这种特定模式,可以明确表达等同但可移植的case语句。但是,它需要有相当多的不同的glob模式来枚举所有的极端情况。

case $foo in
  [![]*  | \[[!0-9]* | *[!][0-9[:space:]]* | *[!0-9[:space:]] | \
  *\]*[![:space:]] | *[!0-9]\]* | \[*\[* | *\]*\]* )
    return 1;;  # false
  \[*[0-9]*\]* )
    return 0;;  # true
  *)
    return 1;;  # false
esac