對於輸入重定向,bash/zsh <<<’$(<file)’ 和傳統的<file 之間是否存在功能差異?
我只詢問與傳統的文件輸入重定向具有類似效果的用法。
<<<"$(<file)"
據我所知,相當於
<file
在我看來,這些在功能上是等效的。在低級別看來,<<< here 文件實際上可能會導致更多的數據副本一次在記憶體中。
我知道這種類型的重定向存在於 bash 和 zsh 中,但我不熟悉它是如何實現的,儘管我看到 zsh 手冊頁包含一些實現細節。
在
<<<"$(<file)"
(由zsh
(第一次引入的地方支持,受 Byron Rakitzis<<<
的 for Unix 的複製中的相同運算符的啟發), (運算符由)和)引入,rc``ksh93``$(<file)``ksh``mksh``bash
對於
$(<file)
,shell 讀取file
(除了 之外的 NUL 字節阻塞zsh
)的內容,刪除所有尾隨換行符並進行擴展$(<file)
(因此文件的內容作為一個整體儲存在記憶體中)。對於
<<< some-text
,shell 將some-text
後跟一個換行符儲存到一個臨時文件中,並在文件描述符 0 上打開該臨時文件(儘管包括最近版本的一些 shellbash
可以使用管道代替,至少對於少量數據)。因此,基本上
<<<"$(<file)"
打開標準輸入以讀取file
尾隨換行符僅被一個替換的臨時副本(如果文件包含 NUL 字節,則會出現各種不當行為,但 in 除外zsh
)。在 中
< file
,它file
是直接打開以在標準輸入上讀取的。當然
< file
效率更高(不涉及磁碟和記憶體中的副本),但可能需要使用<<<"$(<file)"
確保在標準輸入上打開的文件是正常文件,或者確保文件已被完全讀取到命令啟動時(例如,如果該命令寫入它)或處理另一個重定向(如file
在 中截斷的重定向tr 1 2 <<< "$(<file)" > file
)。請注意,它
yash
支持<<<
運算符(儘管使用管道(因此不是正常文件)而不是臨時文件來實現它)。但不是那個$(<file)
。你可以<<<"$(cat < file)"
在那裡使用。yash
字元串只是字元,因此"$(cat < file)"
會阻塞不形成有效字元的字節序列,而其他 shell 通常可以處理它們。