2014-04-28 52 views
1

我运行一个命令,那么左右的代码块将被执行;如果命令失败:命令||运行代码并退出

#!/bin/sh 
test || (
echo "Test failed, exit!" 
exit 1 
) 
echo "Test succeeded!" 

这工作,但剧本只是继续和不退出,Test succeeded仍印刷。

我尝试使用exec

test || exec <<EOS 
    echo "Test failed, exit!" 
EOS 

但是,这并不在所有运行定界符也没有停止脚本休息...

我是很新的shell脚本。

+1

它正在用'()'打开的子shell中退出。 – fedorqui

+0

这就是我的想法,但你可以看到我没有得到exec工作来替换当前的脚本(然后它会从那里退出,对吧?)。我如何运行没有子shell的代码块? – user21033168

+0

使用bash条件,这就是他们的目的。 – jwg

回答

5

这是因为(..)启动了一个子shell。任何与你在里面做的相关的进程只会影响这个子shell。

相反,使用{..}分组:

#!/bin/sh 
test || { 
echo "Test failed, exit!" 
exit 1 
} 
echo "Test succeeded!" 

(..)行为是非常有用的,当你真正要包含的效果,如

for dir in */ 
do 
    (cd "$dir" && make) # This 'cd' will be contained inside the() 
done 

这使您不必保持跟踪您是否能够进入,因此您是否需要cd ..才能让它回到您所在的位置。

+3

+1,完全正确,但我会鼓励OP使用函数来平滑它:'warn(){printf'%s \ n'“$ @”>&2; } die(){local st =“$ 1”;转移;警告“$ @”;退出$ st; }';即两个实用功能:一个发送警告消息给标准错误,另一个发出警告并退出。然后你可以做'测试||死亡$? '测试失败,退出!'' – kojiro

3

@thatOtherGuy给了你正确的答案。

我会鼓励你,作为一个风格问题,如果{ grouped block; }长于一行,使用if

if test; then 
    echo "test succeeded" 
else 
    echo "test failed, exit" >&2 
    exit 1 
fi 

银两,国际海事组织,少可读性。

test || { 
    echo "test failed, exit" >&2 
    exit 1 
} 
echo "test succeeded" 
+0

会做。 15char – user21033168