Shell 脚本是否按顺序执行命令?

Shell 脚本是否按顺序执行命令?

我有一个 python 脚本,它有点不稳定,时不时会出现 SSL 错误。该异常是由某些库中深埋的某些函数引发的,因此基本上没有解决办法。

我通过创建一个带有运行大量次的 while 循环的 shell 脚本并从该循环内执行 python 脚本来实现了一个 hacky 解决方案。

现在我希望的是,当循环的迭代开始并执行脚本时,shell 脚本内的循环保持在原来的位置,直到 python 脚本失败并且循环的下一次迭代重新执行脚本,所以在。

这样做有效率吗?有更好的方法吗?最重要的是它正确吗?

答案1

在:

cmd1
cmd2

或者

cmd1; cmd2

它们是按顺序执行的。

cmd1 && cmd2

或者

cmd1 || cmd2

它们按顺序执行,但是否cmd2执行完全取决于是cmd1成功 (for &&) 还是失败 (for ||)。

cmd1 | cmd2

或者

cmd1 & cmd2
cmd1 |& cmd2 # ksh
coproc cmd1; cmd2 # bash/zsh

或者

cmd1 <(cmd2) # ksh/zsh/bash (also yash though with a different meaning)

它们是同时执行的。在第一种情况下,一些 shell 仅在继续执行脚本的其余部分之前等待,cmd2而另一些 shell 则两者都等待。在第二种情况下,shell 仅等待cmd2cmd1据说是异步运行(或在交互式 shell 中运行时在后台运行)),而在第三种情况下是 for cmd1cmd2异步)。

在:

< "$(cmd1)" x=$(cmd2) y=$(cmd3) cmd4 "$(cmd5)" > "$(cmd6)"

命令按顺序运行,但顺序取决于 shell。无论如何,cmd4都会最后执行。

在:

cmd1 =(cmd2) # zsh

它们按顺序执行(cmd2首先)。

请注意,在所有这些情况下,任何这些命令都可以启动其他进程。 shell 不知道它们,所以不可能等待它们。

答案2

是的。它是正确的。考虑一下:

#!/bin/bash

while true; do
    sleep 1
    echo "Slept 1"
    echo "Exit status $?, ok."
    sleep 1
    echo "Slept 1, now executing faulty command 'ps q'"
    ps q
    echo "Exit status $?, not ok. Loop continues forever..."
done

...执行时将如下所示:

./loop.sh 
Slept 1
Exit status 0, ok.
Slept 1, now executing faulty command 'ps q'
ps: illegal option -- q
usage: ps [-AaCcEefhjlMmrSTvwXx] [-O fmt | -o fmt] [-G gid[,gid...]]
          [-u]
          [-p pid[,pid...]] [-t tty[,tty...]] [-U user[,user...]]
       ps [-L]
Exit status 1, not ok. Loop continues forever...
Slept 1
Exit status 0, ok.
Slept 1, now executing faulty command 'ps q'
ps: illegal option -- q
usage: ps [-AaCcEefhjlMmrSTvwXx] [-O fmt | -o fmt] [-G gid[,gid...]]
          [-u]
          [-p pid[,pid...]] [-t tty[,tty...]] [-U user[,user...]]
       ps [-L]
Exit status 1, not ok. Loop continues forever...
^C

只要循环始终存在,true循环内的程序具有哪些退出代码并不重要。它们将继续按照写入的顺序执行。

这样做有效率吗?有更好的方法吗?

最好的方法就是消除 Python 程序中的错误!

答案3

回答你的标题问题:是的,shell脚本中的命令是按顺序同步执行的,因此当你的Python脚本运行时,shell会被阻止。

修复错误源当然会更好,但如果这不是一个选项,那么 shell 脚本会尝试运行 python 脚本,直到返回零状态代码 ( while true;do ./script.py; if [[ "$?" = 0]];break;done),这是一种明智的方法。

相关内容