tee*_*pee 3 python path python-3.x pathlib
我正在尝试返回特定位置中所有文件和子文件夹的列表。我的代码如下:
from pathlib import Path
FOLDER_PATH = Path(r'C:\long\file\path\of\138\characters\')
Run Code Online (Sandbox Code Playgroud)
我收到错误:
FileNotFoundError: [WinError 3] The system cannot find the path specified:
错误发生在文件夹路径上,而不是文件上,所以我不确定这是否可能是原因。
当我手动进入文件夹并尝试在其中打开文件夹时PDF,我收到“打开此文档时出错。找不到此文件。”
同样,当我尝试打开XLSX文件时,我得到“无法访问此文件。尝试以下操作之一:(确保它存在,不是只读的,不超过 218 个字符等)”
此文件夹中的文件路径肯定超过 218 个字符,我知道这可能是 Excel 的问题,但我不明白为什么pathlib.Path.rglob列出它们会有问题,有人理解吗?
但是,如果我使用CMD( dir /s /b > files.txt) 我可以得到列表。
此外,如果我随后在 python 中导入对象files.txt列表 ,并尝试执行,它将无法将某些较长的路径正确识别为文件。Pathpaths[x.is_file() for x in paths]
我已经验证,如果我在本地复制目录(其中存在更短的路径),则 Excel 和pathlib.Path.rglob.
可以做些什么来解决这个问题,为什么它首先是一个问题?
问题是大多数 Windows 文件系统函数不接受如下所示的路径:
r'C:\long\file\path\of\256\characters'
Run Code Online (Sandbox Code Playgroud)
因此 pathlib 和 Excel 都发现它们无法使用这些 Windows 函数打开文件或读取目录。
好消息是 Windows 函数确实接受如下所示的路径:
r'\\?\C:\long\file\path\of\256\characters'
Run Code Online (Sandbox Code Playgroud)
坏消息是 pathlib 并不总是正确连接此类路径:
>>> Path(r'\\?\foo').joinpath(r'\\?\bar')
WindowsPath('//?/foo/bar') # correct
>>> Path(r'\\?\foo', r'\\?\bar')
WindowsPath('//?/bar') # incorrect
>>> Path(r'\\?\c:\foo').joinpath(r'c:\bar')
WindowsPath('c:/bar') # correct, but not the result we want
Run Code Online (Sandbox Code Playgroud)
另一个坏消息是这样的路径有些限制:当进入 Windows 文件系统函数的路径以 开头时\\?\,不能使用正斜杠或单点或双点。
好消息是,像下面这样的函数几乎可以将您想出的任何杂乱路径转换为有效的路径:
def longname(path):
return pathlib.Path('\\\\?\\' + os.fspath(path.resolve()))
Run Code Online (Sandbox Code Playgroud)
请注意,resolve()仅从if实际存在\\?\的开头删除,因此上面的代码在不存在且已经存在的情况下不起作用。因此,请确保您的程序使用没有前缀的“普通”路径,并在执行任何实际文件操作之前调用作为最后一件事,或者增强:pathpathpath\\?\longname()longname()
def longname(path):
normalized = os.fspath(path.resolve())
if not normalized.startswith('\\\\?\\'):
normalized = '\\\\?\\' + normalized
return pathlib.Path(normalized)
Run Code Online (Sandbox Code Playgroud)
Microsoft 记录了 Windows 行为:https : //docs.microsoft.com/en-us/windows/win32/fileio/naming-a-file#maximum-path-length-limitation