如何讓多個 pv 按照順序堆疊顯示進度條?

原本的指令為:

time python mapper.py < ./data/wiki1G.txt | sort -k1,2 -k3n | python reducer.py > skipgram.tsv

由於這個指令的執行時間很長,我們希望在每個 pipe 中間都插入 pv 來觀察處理進度,以便瞭解電腦是否有正常運作,還是當機。

一開始我直接插入 pv ,結果所有的 output 都擠在同一行,根本無法區分是哪一部分的進度。後來根據 See multiple progress bars at once for multiple pipes with pv Using gzip 的範例,在中間插入:

pv -cN 'name of stage'

其中:
-c 為 cursor 位置游標,用以取代 carriage return,讓多行堆疊
-N 為行首的 prefix 名稱

參考: https://man7.org/linux/man-pages/man1/pv.1.html

結果如下:

time python mapper.py < ./data/wiki1G.txt | pv -cN 'mapper to sort' | sort -k1,2 -k3n | pv -cN 'sort to reducer' | python reducer.py | pv -cN 'to outputfile' > skipgram.tsv
mapper to sort: 2.63GiB 0:06:34 [5.62MiB/s] [        <=>                                                               ]
sort to reducer: 0.00 B 0:06:34 [0.00 B/s] [<=>                                                                        ]
to outputfile: 0.00 B 0:06:34 [0.00 B/s] [<=>                                                                          ]

但有時候進度條的顯示順序會錯亂,根據:  bash - Multiple pv order - Unix & Linux Stack Exchange  ,解決方式為加入一個延遲:

用以下取代上面的 pv -cN 'name of stage' :

(</dev/null sleep 0.1; exec pv -cN 'name of stage')

其中 sleep 0.1 為延遲 0.1 秒,按照出現的順序,不斷往下增加延遲時間:

time python mapper.py < ./data/wiki1G.txt | pv -cN 'mapper to sort' | sort -k1,2 -k3n | (</dev/null sleep 0.1; exec pv -cN 'sort to reducer') | python reducer.py | (</dev/null sleep 0.2; exec pv -cN 'to outputfile') > skipgram.tsv