python os walk复杂度_python os.walk达到一定水平

I want to build a program that uses some basic code to read through a folder and tell me how many files are in the folder.

Here is how I do that currently:

import os

folders = ['Y:\\path1', 'Y:\\path2', 'Y:\\path3']

for stuff in folders:

for root, dirs, files in os.walk(stuff, topdown=True):

print("there are", len(files), "files in", root)

This works great until there are multiple folders inside the "main" folder as it can return a long, junky list of files due to poor folder/file management. So I would like to go only to the second level at most. example:

Main Folder

---file_i_want

---file_i_want

---Sub_Folder

------file_i_want

------file_i want

------Sub_Folder_2

---------file_i_dont_want

---------file_i_dont_want

I know how to go to only the first level with a break and with del dirs[:] taken from this post and also this post.

import os

import pandas as pd

folders = ['Y:\\path1', 'Y:\\path2', 'Y:\\path3']

for stuff in folders:

for root, dirs, files in os.walk(stuff, topdown=True):

print("there are", len(files), "files in", root)

del dirs[:] # or a break here. does the same thing.

But no matter my searching I can't find out how to go two layers deep. I may just not be understanding the other posts on it or something? I was thinking something like del dirs[:2] but to no avail. Can someone guide me or explain to mehow to accomplish this?

解决方案

you could do like this:

depth = 2

# [1] abspath() already acts as normpath() to remove trailing os.sep

#, and we need ensures trailing os.sep not exists to make slicing accurate.

# [2] abspath() also make /../ and , "." get resolved even though os.walk can returns it literally.

# [3] expanduser() expands ~

# [4] expandvars() expands $HOME

stuff = os.path.abspath(os.path.expanduser(os.path.expandvars(stuff)))

for root,dirs,files in os.walk(stuff):

if root[len(stuff):].count(os.sep) < depth:

for f in files:

print(os.path.join(root,f))

key is: if root[len(stuff):].count(os.sep) < depth

It removes stuff from root, so result is relative to stuff. Just count the number of files separators.

The depth acts like find command found in Linux, i.e. -maxdepth 0 means do nothing, -maxdepth 1 only scan files in first level, and -maxdepth 2 scan files included sub-directory.

Of course, it still scans the full file structure, but unless it's very deep that'll work.

Another solution would be to only use os.listdir recursively (with directory check) with a maximum recursion level, but that's a little trickier if you don't need it. Since it's not that hard, here's one implementation:

def scanrec(root):

rval = []

def do_scan(start_dir,output,depth=0):

for f in os.listdir(start_dir):

ff = os.path.join(start_dir,f)

if os.path.isdir(ff):

if depth<2:

do_scan(ff,output,depth+1)

else:

output.append(ff)

do_scan(root,rval,0)

return rval

print(scanrec(stuff)) # prints the list of files not below 2 deep

Note: os.listdir and os.path.isfile perform 2 stat calls so not optimal. In Python 3.5, the use of os.scandir could avoid that double call.

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值