bash 脚本会预解析语法吗?
Will bash script pre-parse the syntax?
我正在 运行ning bash 脚本需要 运行 不同的 SunOs 代码和 Linux 我从代码的一部分中得到语法错误那不应该是真的。我没想到,因为我认为 Bash 可以作为解释器。
SunOS 上的 bash 版本是 2.5,Linux 上的版本是 4.1。它抱怨的语法只支持 3.1 版本。
我试图用 "else" 子句禁用较新的代码,但它看起来仍然在预解析。
而且我的脚本第一行有“:”而不是“#!/bin/sh”。
test.sh:
:
echo "`uname`"
if [ `uname` = "SunOS" ]
then
echo "do old stuff"
else
echo "new stuff"
arr=($(grep "^X1" ../foo.txt | sed 's/.*=//'))
fi
错误是
> ./test.sh
SunOS
./test.sh: syntax error at line 8: `arr=' unexpected
如果我注释错误行,那么它将正常工作:
:
echo "`uname`"
if [ `uname` = "SunOS" ]
then
echo "do old stuff"
else
echo "new stuff"
#arr=($(grep "^X1" ../foo.txt | sed 's/.*=//'))
fi
结果是
> ./test.sh
SunOS
do old stuff
我的问题是如何在不评论的情况下修复此语法错误?我必须 "if/else" 才能在不同的机器上 运行 这个脚本。
您可以将命令放在一个临时变量中,然后在您的条件为真时执行该变量。我只是 运行 我系统上的以下内容:
> if [ true ]; then echo hi; else [blah]=(--4); fi
-bash: syntax error near unexpected token `--4'
如您所述,我遇到语法错误。如果我这样做:
> if [ true ]; then echo hi; else var="[blah]=(--4)" && eval "${var}"; fi
hi
然后回显 hi(没有错误)。最后,如果我这样做:
> if [ ]; then echo hi; else var="[blah]=(--4)" && eval "${var}"; fi
-bash: syntax error near unexpected token `--4'
然后它尝试 运行 代码,并根据尝试 运行 代码生成错误。
bash 至少从第 2 版开始支持该数组语法;如果您在那里遇到错误,那是因为您的脚本根本不是 运行ning 在 bash 下,而是在其他一些 shell 下。这可能与你的脚本以 :
开头而不是 shebang 行有很大关系,这意味着它取决于 运行 脚本来弄清楚 运行 它用什么,用不一致的结果。我强烈建议使用合适的 shebang 系列。如果 bash 不存在于可预测的位置,您可以使用 #!/usr/bin/env bash
。如果 bash 可能不在 PATH
中,您可以使用脚本序言 here 之类的东西——一个 #!/bin/sh
shebang,然后是命令来查找并切换到 bash.
关于预解析的问题:是的,bash等shell会在执行if
之前一直解析到fi
关键字构造。他们需要找到 then
、else
和 fi
关键字,以便弄清楚他们将要执行什么以及将要跳过什么,并且为了找到那些他们必须解析他们的方式。
我正在 运行ning bash 脚本需要 运行 不同的 SunOs 代码和 Linux 我从代码的一部分中得到语法错误那不应该是真的。我没想到,因为我认为 Bash 可以作为解释器。
SunOS 上的 bash 版本是 2.5,Linux 上的版本是 4.1。它抱怨的语法只支持 3.1 版本。
我试图用 "else" 子句禁用较新的代码,但它看起来仍然在预解析。
而且我的脚本第一行有“:”而不是“#!/bin/sh”。
test.sh:
:
echo "`uname`"
if [ `uname` = "SunOS" ]
then
echo "do old stuff"
else
echo "new stuff"
arr=($(grep "^X1" ../foo.txt | sed 's/.*=//'))
fi
错误是
> ./test.sh
SunOS
./test.sh: syntax error at line 8: `arr=' unexpected
如果我注释错误行,那么它将正常工作:
:
echo "`uname`"
if [ `uname` = "SunOS" ]
then
echo "do old stuff"
else
echo "new stuff"
#arr=($(grep "^X1" ../foo.txt | sed 's/.*=//'))
fi
结果是
> ./test.sh
SunOS
do old stuff
我的问题是如何在不评论的情况下修复此语法错误?我必须 "if/else" 才能在不同的机器上 运行 这个脚本。
您可以将命令放在一个临时变量中,然后在您的条件为真时执行该变量。我只是 运行 我系统上的以下内容:
> if [ true ]; then echo hi; else [blah]=(--4); fi
-bash: syntax error near unexpected token `--4'
如您所述,我遇到语法错误。如果我这样做:
> if [ true ]; then echo hi; else var="[blah]=(--4)" && eval "${var}"; fi
hi
然后回显 hi(没有错误)。最后,如果我这样做:
> if [ ]; then echo hi; else var="[blah]=(--4)" && eval "${var}"; fi
-bash: syntax error near unexpected token `--4'
然后它尝试 运行 代码,并根据尝试 运行 代码生成错误。
bash 至少从第 2 版开始支持该数组语法;如果您在那里遇到错误,那是因为您的脚本根本不是 运行ning 在 bash 下,而是在其他一些 shell 下。这可能与你的脚本以 :
开头而不是 shebang 行有很大关系,这意味着它取决于 运行 脚本来弄清楚 运行 它用什么,用不一致的结果。我强烈建议使用合适的 shebang 系列。如果 bash 不存在于可预测的位置,您可以使用 #!/usr/bin/env bash
。如果 bash 可能不在 PATH
中,您可以使用脚本序言 here 之类的东西——一个 #!/bin/sh
shebang,然后是命令来查找并切换到 bash.
关于预解析的问题:是的,bash等shell会在执行if
之前一直解析到fi
关键字构造。他们需要找到 then
、else
和 fi
关键字,以便弄清楚他们将要执行什么以及将要跳过什么,并且为了找到那些他们必须解析他们的方式。