[转载] Python递归遍历目录下所有文件查找指定文件

参考链接: Python目录和文件管理

之前看到网上有人说『os.path.isdir()判断必须写绝对路径』,当时心想Python不是有迭代上下文吗,为什么不行?遂作本文验证之 

 

 

代码部分 

考虑用一个path变量指代当前遍历元素的绝对路径(正确做法) 

def search(root, target):

    items = os.listdir(root)

    for item in items:

        path = os.path.join(root, item)

        if os.path.isdir(path):

            print('[-]', path)

            search(path, target)

        elif path.split('/')[-1] == target:

            print('[+]', path)

        else:

            print('[!]', path)

 

正常遍历的结果 

 

如果这样写,把路径全部换成item(迭代元素) 

def search(root, target):

    items = os.listdir(root)

    for item in items:

        if os.path.isdir(item):

            print('[-]', item)

            search(os.path.join(root, item), target)

        elif item == target:

            print('[+]', os.path.join(root,item))

        else:

            print('[!]', os.path.join(root, item)) 

 

可以看出,这是行不通的:如果使用item迭代元素进行指代当前路径,最多只会再往下递归两层(子文件夹、子文件夹的文件),可见所未的上下文管理机制在这里是完全不起作用的 

反思和总结 

1)如果在正确遍历写法基础上,仅改变每次递归时的传递元素迭代机制会做出怎样的反应? 

在上面的例子中,只需要把search(os.path.join(root, item), target)改成search(item, target)即可: 

 

这一点很容易看出,因为在首次调用search(..)函数时就是传入了一个绝对路径,如果传入相对路径因为没有上下文环境,是不能正确定位文件位置的 

2)os.path.abspath(path)方法可以替代os.path.join(root, current)吗? 

实践出真知: 

 

(大雾)原来os.path.abspath(..)表示的是:相对当前工作目录的相对路径!(而不是相对系统根目录的相对路径!) 

所以,os.path.abspath(..)和os.path.join(..)是两个完全不同的东西,是不能替换的 

3)Python的文件到底是什么呢? 

还是那份正确的代码,将每一条输出改成用type(..)函数包裹的形式 

 

在看下面另一个例子 

 

本着Python中『一切皆对象』的信念,我们输入的路径(包括它的迭代版本、用来接受它的变量)是一个字符串str对象,而用来描述文件的文件句柄(指针)则是一个_io.TextIOWrapper类型的对象 

通常我们在文件夹、文件水平查找、筛选,用的是str类型的路径描述,而要对具体某个文件(不是文件夹)进行读或写的操作,就要用到_io.TextIOWrapper类型的文件句柄,它们分的比较细;不像Java中完全被封装成了一个File(String path)对象,它弱化了文件路径的作为单独个体的作用——但是Python则把路径单独拎出来,我们很多的文件操作(广义上比如查找指定文件,不单指文件IO),都是建立在文件路径的基础上的 

4)思考:除了开头给出的方法,有没有别的遍历文件办法? 

答案是:有的(yes) 

 

os.chdir(path)函数可以改变当前工作目录到指定path 

但是我们不推荐使用该方法,因为它修改了全局变量,这一点在函数调用前后使用os.getcwd()函数进行验证 

先把工作目录切换到根目录下,接着执行自定义的change()函数 

 

如你所见,这时候全局的当前工作目录已经发生了改变

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值