當我在符號連結文件夾中時,從父位置複製文件
假設我在 call 和 中創建了兩個
/tmp
文件parent
夾child
。child
包含一個名為的文件test-child.txt
,並parent
包含一個名為test-parent.txt
. 現在讓我們進入內部parent
並創建一個指向child
. 接下來,進入child
並嘗試test-parent.txt
從parent
. bash 完成工作,但實際文件複製失敗——cd /tmp pwd /tmp mkdir parent mkdir child touch child/test-child.txt ls child/ test-child.txt cd parent ln -sf ../child . touch test-parent.txt cd child cp ../test-parent.txt . cp: cannot stat ‘../test-parent.txt’: No such file or directory
為什麼 ??
此外,當我在裡面時
child
,如果我說——pwd /tmp/parent/child
為了方便使用者,Shell 會跟踪符號連結。這具有
cd foo && cd ..
始終返回原始目錄的良好效果,即使foo
是指向目錄的符號連結也是如此。它有兩種缺點:主要的一個是其他程序不這樣做。此外,符號目錄跟踪會引入其自身的問題(當符號連結更改時會發生什麼?如果程序沒有讀取符號連結的權限會發生什麼?等等)。Shell 只能這樣做,因為它們會跟踪所有目錄更改,因此它們會記住您是如何到達那裡的。當一個新程序開始時,它不會得到這個歷史資訊。在引擎蓋下,它通過從目前目錄向上移動來找到它所在的位置,跟隨
..
連結直到它到達根目錄¹。如果您通過符號連結到達一個目錄,您可以
pwd
通過呼叫pwd -P
. 如果您從 shell 呼叫另一個程序,請不要將包含..
符號連結組件之後的路徑傳遞給它,因為該程序會以不同的方式解釋它。..
相反,通過呼叫消除組件pwd -P
:cp "$(cd .. && pwd -P && echo /)test-parent.txt" .
如果您想忘記
cd
shell 會話中過去命令中使用的符號連結,您可以執行cd "$(pwd -P && echo /.)"
這將更改為已經是目前目錄的內容,因此它不會有效地更改 shell 程序的目前目錄,但它會更改 shell 為目前目錄跟踪的路徑,使其無符號連結。
¹這就是
getcwd
呼叫傳統上的運作方式。一些核心確實跟踪目前目錄,但不跟踪符號連結,如果沒有其他原因(但也因為符號連結的微妙邊緣情況),為了向後兼容。