一次運行多個命令

一次運行多個命令

我需要在盡可能短的時間內運行大量類似的命令並使用所有可用資源。

例如,我的情況是處理圖像,當我使用以下命令時: for INPUT in *.jpg do; some_command; done該命令被一一執行,並且不使用所有可用資源。

但另一方面,執行for INPUT in *.jpg do; some_command &; done會使機器在很短的時間內耗盡資源。

我知道 的at命令batch,但我不確定是否可以在我的情況下使用它。如果我錯了請糾正我。

所以我正在考慮將命令放入某種隊列中並立即執行其中的一部分。我不知道如何快速做到這一點,這就是問題所在。我確信以前有人遇到過類似的問題。

請指教。

答案1

GNU Parallel 正是為此而設計的:

parallel some_command {} ::: *.jpg

預設情況下,每個 CPU 核心執行一項作業。在您的情況下,您可能希望比您擁有的核心多運行一項作業:

parallel -j+1 some_command {} ::: *.jpg

GNU Parallel 是一個通用並行器,可以輕鬆地在同一台電腦或多台您可以透過 ssh 存取的電腦上並行運行作業。

如果您想要在 4 個 CPU 上執行 32 個不同的作業,則並行化的直接方法是在每個 CPU 上執行 8 個作業:

簡單的調度

相反,GNU Parallel 在完成後會產生一個新進程 - 保持 CPU 處於活動狀態,從而節省時間:

GNU 平行調度

安裝

出於安全原因,您應該使用軟體套件管理器安裝 GNU Parallel,但如果 GNU Parallel 未針對您的發行版打包,您可以進行個人安裝,這不需要 root 存取權限。這樣做可以在 10 秒內完成:

(wget -O - pi.dk/3 || curl pi.dk/3/ || fetch -o - http://pi.dk/3) | bash

其他安裝選項,請參閱http://git.savannah.gnu.org/cgit/parallel.git/tree/README

了解更多

查看更多範例:http://www.gnu.org/software/parallel/man.html

觀看介紹影片:https://www.youtube.com/playlist?list=PL284C9FF2488BC6D1

瀏覽本教學:http://www.gnu.org/software/parallel/parallel_tutorial.html

註冊電子郵件清單以獲得支援:https://lists.gnu.org/mailman/listinfo/parallel

答案2

您可以使用 GNU make 並--jobs選擇並行運行,但僅限於指定的作業數量。您可以將該數字調整為不會殺死您的機器的值。

這是一個範例 Makefile,它使用目標 ah(這些可能是您的輸出文件,例如)並為每個目標執行一組(虛擬)命令:

all: a b c d e f g h

a b c d e f g h:
    echo $@; sleep 10

注意命令的縮排必須是一個 TAB 字元。請參閱GNU make 文檔有關 Makefile 語法的詳細資訊。

您可以呼叫 makemake --jobs 4並獲得以下輸出(我time make --jobs 4在下面使用它來顯示經過的時間):

echo a; sleep 10
echo b; sleep 10
echo c; sleep 10
echo d; sleep 10
b
a
c
d
echo e; sleep 10
echo f; sleep 10
echo g; sleep 10
e
f
echo h; sleep 10
g
h

real    0m20.009s
user    0m0.010s
sys 0m0.011s

前四個並行執行,然後是接下來的四個,因此總耗時為 20 秒。

相關內容