windows路径长度限制260字符,需系统启用longpathsenabled并用\?前缀配合绝对路径;os.scandir()比os.listdir()更安全,pathlib需手动拼接前缀,避免abspath()清除前缀。

Windows 默认路径长度限制为 260 字符,Python 的 os 和 pathlib 在未启用长路径支持时会直接报错(如 FileNotFoundError 或 OSError: [WinError 206] The filename or extension is too long)——这不是 Python 的 bug,而是 Windows API 层的限制,必须从系统和代码两层同时处理。
启用 Windows 长路径支持(系统级前提)
Python 无法绕过未开启的系统限制。即使代码写对了,CreateFileW 等底层 Win32 调用仍会拒绝超长路径。
- 修改注册表:
HKEY_LOCAL_MACHINESYSTEMCurrentControlSetControlFileSystemLongPathsEnabled设为1(DWORD) - 或通过组策略:「计算机配置 → 管理模板 → 系统 → 文件系统 → 启用 Win32 长路径」设为已启用
- 重启资源管理器或整个系统(部分场景需重启生效)
- 验证是否生效:在 PowerShell 中运行
Get-ItemProperty HKLM:SYSTEMCurrentControlSetControlFileSystem -Name LongPathsEnabled,值应为1
Python 中使用 \? 前缀访问超长路径
这是最直接、兼容性最好的方式:绕过 Windows 路径解析层,交由 NT 内核直接处理。所有标准库 I/O 函数(open()、os.listdir()、shutil.copy() 等)都支持该前缀,但要求路径是绝对路径且无相对组件(如 ..)。
- 必须用原始字符串避免转义:
r"\?C:erylongpath..." - 不能混用斜杠/反斜杠:统一用
,且开头必须是\?+ 驱动器号 +: -
pathlib.Path不自动添加该前缀,需手动拼接:Path(r"\?" + str(full_path.resolve())) - 注意:
os.path.abspath()会去掉\?,不要对已加前缀的路径再调用它
用 os.scandir() 替代 os.listdir() 处理深层嵌套目录
os.listdir() 在遇到超长子路径时可能提前失败;os.scandir() 返回 DirEntry 对象,其 path 属性可安全携带 \? 前缀,且延迟解析,更适合遍历。
- 正确做法:先构造带
\?的根路径,再传给os.scandir() - 示例:
root = r"\?C:erydeepolderwithmanysubdirs" for entry in os.scandir(root): if entry.is_file(): # entry.path 已含 \? 前缀,可直接 open(entry.path) with open(entry.path, "rb") as f: pass - 避免:
os.walk()默认不支持前缀,需手动包装逻辑,否则中途可能崩溃
第三方库如 pathlib2 或 pywin32 并不解决根本问题
很多开发者试图用新库“绕过”限制,但实际无效:
-
pathlib2是旧版pathlib的 backport,不改变底层 Win32 行为 -
pywin32的win32file模块虽提供更底层接口,但仍需显式传入\?前缀,且多数函数(如CreateFile)参数格式复杂,易出错 - 依赖
shutil的操作(如copytree)默认不传递前缀,需重写逻辑或改用distutils.dir_util.copy_tree(已弃用)或自行递归处理
真正卡住人的地方往往不是代码怎么写,而是忘了改注册表,或者拼了 \? 却用了 / 斜杠、混了相对路径、又调了一次 abspath() 把前缀干掉了——这些细节比语法本身更容易导致失败。
Python免费学习笔记(深入):立即使用
在学习笔记中,你将探索 Python 的核心概念和高级技巧!











