如何防止Python的os.walk跨越挂载点?

11

https://dev59.com/lEbRa4cB1Zd3GeqP04Hj#530692 - sykora
3个回答

19

来自os.walk文档:

当topdown为True时,调用者可以原地修改dirnames列表 (可能使用del或切片分配),并且walk()仅会递归到其名称仍在dirnames中的子目录中; 这可用于修剪搜索

因此,像这样做应该可以:

for root, dirnames, filenames in os.walk(...):
  dirnames[:] = [
    dir for dir in dirnames
    if not os.path.ismount(os.path.join(root, dir))]
  ...

一个非常简洁的答案。 - Matt Joiner
如其他评论所述:您可以通过在另一个文件系统中更深的符号链接来欺骗它。更好的方法是保存初始路径的st_dev(例如dev0 = os.stat(startpath).st_dev),并过滤为dirnames[:] = [d for d in dirnames if os.stat(os.path.join(root,d)).st_dev == dev0] - Justin Winokur

3
我认为os.path.ismount可以适合您的需求。你的代码可能看起来像这样:
import os
import os.path
for root, dirs, files in os.walk('/'):
    # Handle files.
    dirs[:] = filter(lambda dir: not os.path.ismount(os.path.join(root, dir)), 
                  dirs)

您可能会发现这个答案对于构建您的解决方案很有帮助。

*感谢有关正确过滤dirs的评论。


你可以通过将代码更改为“dirs[:] = filter(...)”来解决这个问题,直接在原地修改列表而不是重新分配。 - Brian
你可以通过在另一个文件系统中更深的符号链接来欺骗它。更好的方法是保存初始路径的st_dev(例如dev0 = os.stat(startpath).st_dev),并过滤为dirs[:] = [d for d in dirs if os.stat(os.path.join(root,d)).st_dev == dev0] - Justin Winokur

1

os.walk() 无法判断(据我所知)它是否正在浏览不同的驱动器。您需要自行检查。

尝试使用 os.stat(),或检查来自 os.walk() 的根变量是否不是 /media


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接