【问题标题】:Syntax error =~ operator in msysgit bashmsysgit bash 中的语法错误 =~ 运算符
【发布时间】:2013-03-19 20:45:14
【问题描述】:

我正在尝试为 添加一个函数到我的bash_profile

function git-unpushed {
    brinfo=$(git branch -v | grep git-branch-name)
    if [[ $brinfo =~ ("[ahead "([[:digit:]]*)]) ]]
    then
        echo "(${BASH_REMATCH[2]})"
    fi
}

但我收到以下错误:

bash:需要条件二元运算符`

bash:=~' 附近的语法错误

据我所知,“等于波浪号”运算符 (=~) 在 bash 中计算为正则表达式。

为什么=~ 会抛出错误?

更新:这是手动输入的截图(这是运行 sh.exe):

【问题讨论】:

  • 不需要引用或将正则表达式放在括号内,只需使用例如[[ $line =~ ^$ ]]
  • 很好,你shebang是什么样子的? /bin/sh 是什么符号链接?
  • @FredrikPihl:因为这是在bash_profile,我怀疑是否有shebang。
  • doh
  • 我已经更新了我的answer below:现在,Windows 的 git 可以很好地使用这种语法。

标签: msysgit windows bash msysgit


【解决方案1】:

我在 Windows 上安装 Git 时在 Bash 3.1.0 上遇到了同样的错误。最终我把它改成了:

if echo $var | grep -E 'regexp' > /dev/null
then
  ...
fi

【讨论】:

    【解决方案2】:

    根据https://groups.google.com/forum/#!topic/msysgit/yPh85MPDyfE,这是因为 msys 没有将 libregex 与 bash 一起提供。假设你编译/找到一个 msys 构建的 libregex,并将其放在库路径中,=~ 开始工作正常。

    【讨论】:

    • 伟大的指针。不幸的是,简单地将 msysgit 的 msys-regex-1.dll 替换为来自 MSYS 的 @ 并起作用。 似乎 的工作原理(尝试自担风险)是将以下文件从 MSYS 安装的 bin 目录复制到 msysgit 的 bin 目录:bash.exesh.exe、@ 987654329@ - 换句话说:完全替换 bash。但是,此时您也可以直接使用 MSYS,仅使用来自 msysgit 的 git.exe - 请参阅 stackoverflow.com/q/5885393/45375
    【解决方案3】:

    2015 年更新:msysgit 现已过时。
    您应该使用 git-for-windows 附带的 bash。
    正如this answer 中提到的,它使用更新的bash (4.3+),=~ 语法适用。


    原始答案(2013 年 3 月)

    使用 msysgit 打包的 bash 可能太旧,无法完全支持此运算符。
    如“Bash, version 3”和“How do I use regular expressions in bash scripts?”中提到的,它确实太旧了无法与未引用正则表达式进行比较:

    从 Bash 3.2 版开始,不再引用要匹配的表达式。

    实际上,mklement0 在 cmets 中提到:

    =~ 是在 bash 3.0 中引入的,并且始终支持 RHS 上不带引号的标记。
    在 3.1.x 之前,带引号的标记被视为与不带引号的标记相同:两者都被解释为正则表达式。
    3.2 中的变化是引用标记(或标记的引用子字符串)现在被视为 literals

    但我尝试使用引号(在最新的 msysgit 1.8.1.2 中),它仍然失败:

    vonc@voncvb /
    $ /bin/bash --version
    GNU bash, version 3.1.0(1)-release (i686-pc-msys)
    Copyright (C) 2005 Free Software Foundation, Inc.
    vonc@voncvb /
    $ variable="This is a fine mess."
    vonc@voncvb /
    $ echo "$variable"
    This is a fine mess.
    vonc@voncvb /
    $ if [[ "$variable" =~ T.........fin*es* ]] ; then echo "ok" ; fi
    bash: conditional binary operator expected
    bash: syntax error near `=~'
    vonc@voncvb /
    $ if [[ "$variable" =~ "T.........fin*es*" ]] ; then echo "ok" ; fi
    bash: conditional binary operator expected
    bash: syntax error near `=~'
    vonc@voncvb /
    

    【讨论】:

    • Re“太旧了,无法与未引用的正则表达式进行比较”:=~ 是在 bash 3.0 中引入的,并且始终支持 RHS 上的 未引用令牌.在 3.1.x 之前,quoted 标记被 视为与未引用标记相同:两者都被解释为正则表达式。 3.2 中的变化是 quoted 标记(或标记的引用子字符串)现在被视为 literals
    • @mklement0 好点。我已将您的评论包含在答案中以提高知名度。
    【解决方案4】:

    这是一个支持提取匹配字符串的解决方案。如果bash不支持运算符=~,则使用sed命令(随msysgit安装)

    if eval "[[ a =~ a ]]" 2>/dev/null; then
        regexMatch() { # (string, regex)
            eval "[[ \$1 =~ \$2 ]]"
            return $?
        }
    elif command -v /bin/sed >/dev/null 2>&1; then
        regexMatch() { # (string, regex)
            local string=$1
            if [[ ${2: -1} = $ ]]; then
                local regex="(${2%$})()()()()()()()()$"
            else
                local regex="($2)()()()()()()()().*"
            fi
            regex=${regex//\//\\/}
            local replacement="\1\n\2\n\3\n\4\n\5\n\6\n\7\n\8\n\9\n"
            local OLD_IFS=$IFS
            IFS=$'\n'
            BASH_REMATCH=($(echo "$string" | /bin/sed -rn "s/$regex/$replacement/p" | while read -r; do echo "${REPLY}"; done))
            IFS=$OLD_IFS
            [[ $BASH_REMATCH ]] && return 0 || return 1
        }
    else
        error "your Bash shell does not support regular expressions"
    fi
    

    使用示例:

    if regexMatch "username@host.domain" "(.+)@(.+)"; then
        echo ${BASH_REMATCH[0]}
        echo ${BASH_REMATCH[1]}
        echo ${BASH_REMATCH[2]}
    fi
    

    【讨论】:

    • 请注意,没有人再使用 msygit:它现在已经过时并被 git-for-windows (github.com/git-for-windows/git/releases) 取代,后者具有更新的 bash 4.x (stackoverflow.com/a/26826359/6309)跨度>
    • 哇,我不后悔改用 Linux。
    • @Vonc 在处理了一段时间的这种精神错乱之后(我想我第一次遇到它是在 8 月),我只是试了一下 git-for-windows,对有多少愚蠢感到震惊它修复了与 msysgit 相比的烦恼(例如,vim 缺少任何智能默认值,缺少可调整大小的终端等)。我想我在 2011 年或 2012 年开始使用 msysgit 并且不知道有什么更好的(也许当时没有?)。老实说,我不知道为什么这个建议被隐藏在评论中——也许你应该考虑把它作为一个答案?恕我直言,这是最好的答案。
    • @DavidGoldstein 我什至没有注意到我在 3 年前就在这个页面上给出了答案!我已经更新了我的旧答案,以更清楚地了解 Windows 使用哪个 git 发行版。
    猜你喜欢
    • 1970-01-01
    • 2018-09-19
    • 2012-10-01
    • 1970-01-01
    • 2018-07-21
    • 2012-11-19
    • 1970-01-01
    • 1970-01-01
    • 2013-11-01
    相关资源
    最近更新 更多