我正试图弄清楚为什么在Bash脚本中备份大量进程时,速度回报会递减。类似于:
function lolecho() {
echo "lol" &> /dev/null
}
c=0
while true; do
for i in $(seq 1 1000); do
lolecho &
((c+=1))
if [[ $((c%1000)) -eq 0 ]]; then
echo "Count $c"
fi
done
sleep .1
done
它尖叫着走出大门,高达1万、20万……但随后它开始放慢速度,它可以以多快的速度建立大约7万…80万的后台流程。与中一样,计数打印到屏幕的速度会减慢一个看似线性的量,具体取决于总数。
无论添加和关闭了多少后台作业,机器运行基本上立即完成的后台作业的速度难道不应该保持一致吗?
答案是使用Linux内置的等待命令:
function lolecho() {
echo "lol" &> /dev/null
}
c=0
while true; do
for i in $(seq 1 1000); do
lolecho &
((c+=1))
if [[ $((c%1000)) -eq 0 ]]; then
echo "Count $c"
fi
done
wait # <------------
done
该脚本现在生成的进程总体上一致且更快。
注释有点长。。。OP使用wait
命令的解决方案很好,但可能会微调一点。。。
按编码(在作战人员的回答中(:
- 产生了1K后台进程(可能会对系统资源产生一些争用(
- 我们等待所有1K过程完成,然后
- 启动一组新的1K流程
为了获得更一致的吞吐量,我想:
- 考虑限制并发后台进程的数量(例如,50?100?(;将需要在您的特定系统上运行一些测试(以减少系统资源争用,然后
- 使用
wait -n
在进程完成后立即启动新进程
当然,对于这个简单的例子(lolecho()
(来说,这可能没有太大区别,但如果做一些实际的工作,你应该会发现你保持了相当稳定的工作量。
使用wait -n
的几个例子:这里和这里——见答案的后半部分
如果使用不支持-n
标志的旧版本的bash
,则使用轮询过程的示例