【问题标题】:Weird parallel execution in bash scriptbash脚本中奇怪的并行执行
【发布时间】:2017-01-06 03:05:05
【问题描述】:

我正在尝试编写一个 bash 脚本,作为实验的一部分并行回显 2 个变量的值,然后再编写一个 shell 脚本,该脚本为我的项目生成并行附加数字的文件。

这里是shell脚本:

#!/bin/bash

value1=0
value2=1
for i in $(seq 1 2); do
    echo "Value 1 : " $((++value1)) &
    echo "Value 2 : " $((++value2))
    wait
    echo "Wait"
    done

这是我得到的输出:

Value 2 :  2
Value 1 :  1
Wait
Value 2 :  3
Value 1 :  1
Wait

我知道 GNU 并行和 xargs,但我不想使用它们。

我想知道为什么“value2”首先打印,为什么“value1”从不增加。

【问题讨论】:

  • 删除 & 后会发生什么?
  • @KraangPrime 那么输出与预期一致。但我想并行执行此操作,因此 '&'
  • value1 永远不会增加,因为后台进程在子 shell 中运行,对值所做的任何更改都不会报告回父 shell。 value2 可能首先被打印出来,因为 shell 在子 shell 设法使其思想有序并产生输出之前处理下一行执行,但不能保证该顺序。这两个进程并行运行,任何一个都可以赢得回声竞赛。
  • 您将处理value1 的行设置为背景。执行的主线程仍然存在,而后台进程作为一个单独的 shell 被分叉。想象一下,如果value1++ 需要一段时间来处理。在主脚本的执行过程中,您希望该变量在什么时候发生变化,以及实际上会导致它发生变化的原因是什么?如果脚本的其他行正在使用和更改该变量怎么办?
  • 而且.. 是的,总有一种方法可以让你做事,尽管这种方法可能很痛苦,尤其是在 shell 脚本中。如果您希望能够触发后台进程并将其返回给主脚本,您可以让脚本将其输出记录到临时文件中,然后让后台进程发送信号(使用kill)到将执行trap 的主进程。或者您可以通过命名管道将结果发回。当然,可能还有另一种方法可以并行化您正在尝试做的任何事情。我没有足够的信息来提出建议。

标签: bash shell terminal


【解决方案1】:

value1 递增,但在一个单独的过程中。 value1在原流程中没有被修改。无法保证您将首先看到哪个值;两个echo 语句发生在两个不同的进程中,这些进程在操作系统的一时兴起。

【讨论】:

  • 不是在子进程启动之前完成命令行解析吗?我本来希望主进程首先解决参数替换(这会将行转换为echo Value 1 : 1,然后让这个命令在子进程中运行。因此,value 的更改应该是在进程中可见,子进程甚至看不到这个名字的shell变量。
  • 已解析,是的;评估,没有。 shell 尽快分叉。
  • 又学到了一些东西。毕竟是有道理的。如果不是这样,a $(b) & 之类的命令将在前台执行 b
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2018-04-06
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-10-10
相关资源
最近更新 更多