首页 > 解决方案 > 在 Windows CMD 中更改卷时 sys.path 中的奇怪行为

问题描述

我刚刚注意到sys.pathWindows CMD 的一些奇怪行为,想知道发生了什么以及为什么。

在以下两个示例中,我打印出sys.path,将音量更改为D:cd进入目录,将音量更改回C:,最后sys.path再次打印出来。我用两个非常相似PYTHONPATH的 s 来做这个。

PYTHONPATH=D:\

C:\Users\z003w3we>python -c "import sys; print(sys.path)"
['', 'D:\\', <others>]

C:\Users\z003w3we>D:

D:\>cd UserData

D:\UserData>C:

C:\Users\z003w3we>python -c "import sys; print(sys.path)"
['', 'D:\\', <others>]

一切都如预期的那样。

使用PYTHONPATH=D:(注意缺少尾随\):

C:\Users\z003w3we>python -c "import sys; print(sys.path)"
['', 'D:\\', <others>]

C:\Users\z003w3we>D:

D:\>cd UserData

D:\UserData>C:

C:\Users\z003w3we>python -c "import sys; print(sys.path)"
['', 'D:\\UserData', <others>]

C:\Users\z003w3we>echo %PYTHONPATH%
D:

现在,D:我们突然有了D:\UserData,而不是sys.path。注意那PYTHONPATH是不变的。

我无法使用 PowerShell 重现相同的行为;两者都PYTHONPATH表现出第一个行为。

正如我所说,我会对了解这里发生的事情非常感兴趣。

标签: pythonwindowscmd

解决方案


CMD 为驱动器 D: 上的工作目录设置了一个名为“=D:”的传统隐藏环境变量。Python 进程继承此环境变量,Windows API 在GetFullPathNameW调用时使用它来将驱动器相对路径“D:”解析为完全限定路径。

在 CMD 中,我们可以通过 set "" 列出所有环境变量,包括“隐藏”的变量。这个命令依赖于一个错误,但它已经存在了很长时间,以至于它现在是一个特性。要仅列出隐藏的,请使用set "" | findstr /r "^=". 例如:

C:\>set "" | findstr /r "^="
=C:=C:\

C:\>cd /d E:\UserData
E:\UserData>c:

C:\>set "" | findstr /r "^="
=C:=C:\
=E:=E:\UserData

C:\>set PYTHONPATH=E:
C:\>python -c "import sys; print(sys.path[1]); sys.exit(0xFF)"
E:\UserData

C:\>set "" | findstr /r "^="
=C:=C:\
=E:=E:\UserData
=ExitCode=000000FF

推荐阅读