Shell

管道外殼程序如何平衡其輸出/輸入速率?

  • June 29, 2014

可能重複:

Bash while 循環和從管道讀取

我來自 web 程式背景,發現自己對使用本地 shell 的一個特點很感興趣。我知道當程序從文件中讀取時,它可以以任何必要的速率讀取。但是我很想知道,當一個程序通過管道輸入其他程序的輸入並且無法實時處理它時,它是如何工作的?

一個很好的例子是影片編碼。假設我將解碼器指向影片文件,然後它的輸出作為編碼器的輸入通過管道輸入。解碼影片的總大小超過 ram+swap,所以我想沒有辦法將它完全緩衝。我發現了對標準輸入和標準輸出的讀寫呼叫,但我很想知道當這個例子的編碼器不能同時處理所有數據時實際發生了什麼。它是否以某種方式通知解碼器所需的速率?解碼器程序是否需要專門為此類信號准備並相應地修改其處理速度?如果沒有,最終如何平衡?

當寫入器寫入管道並且管道已滿(其大小限制為幾千字節)時,它的程序會阻塞,直到其中一個讀取器釋放一些空間。類似地,當閱讀器從管道中讀取數據時,它的程序會阻塞,直到那裡有東西。

還有非同步寫入和讀取,程序員可以使用這些非同步寫入和讀取來對這些讀取和寫入進行排隊。

我強烈建議閱讀Beej 的指南,從 Beej 的Unix 程序間通信指南開始

你用兩個參數呼叫它,第一個是作者的睡眠時間,第二個是讀者的睡眠時間。嘗試使用 args0 33 0

#!/bin/sh
write_sleep=$1
read_sleep=$2
writer(){
 echo writing output >&2
 echo hi
 sleep $write_sleep
 echo writing output >&2
 echo hi
 sleep $write_sleep
 echo writing output >&2
 echo hi
 sleep $write_sleep
}
reader(){
 while true; do
   echo getting input >&2
   read input
   [ $input ] || { echo input is empty >&2 &&  break; }
   echo $input
   sleep $read_sleep
 done
}

writer | reader

引用自:https://unix.stackexchange.com/questions/53189