简体   繁体   English

Python-Os.walk遍历不同驱动器中的目录列表

[英]Python - Os.walk loop through list of directories in different drives

I'm a Python beginner and looking for some help with searching a list of directories using os.walk. 我是一名Python初学者,正在寻找有关使用os.walk搜索目录列表的帮助。

The idea is that I'm pulling a list of directories from an SQL database, these directories will likely have different drive letters or even a UNC path. 我的想法是从SQL数据库中提取目录列表,这些目录可能具有不同的驱动器号甚至UNC路径。 What I need to do is search through those directories to find a file of a specific name and delete it. 我需要做的是在这些目录中搜索以找到特定名称的文件并将其删除。 As the file could be in any of the directories it needs to search them all. 由于文件可以在任何目录中,因此需要全部搜索。 The list of directories is indefinite so my thought was to store them into a list and have os.walk look at all directories in that list. 目录列表是不确定的,因此我的想法是将它们存储到列表中,并让os.walk查看该列表中的所有目录。

def get_location():
    c.execute('SELECT ADDRESS FROM DIRECTORY')
    data = c.fetchall()
    SQLlist = [row for row in data]
    return SQLlist


addresslist = get_location()


def FileDeleter():
    for root, dirs, files in chain.from_iterable(os.walk(addresslist[0:], topdown=False) for path in (str(addresslist[0:]))):
        for file in files:
            if correctID in file:
                if file.endswith('.custextn'):
                    os.remove(os.path.join(root, file))

This is how the code currently stands, but previously I've tried: 这是当前代码的样子,但是以前我尝试过:

    for root, dirs, files in os.walk(addresslist[0:], topdown=False):

    for root, dirs, files in chain.from_iterable(os.walk(addresslist[0:], topdown=False)):

It seems to be that os.walk doesn't accept lists (/ tuples). 似乎os.walk不接受列表(/元组)。 If I set addresslist[0] or addresslist[1] it actually works, however as I don't know how many addresses there potentially could be I unfortunately can't just store X addresses as separate variables and duplicate the function. 如果我设置addresslist [0]或addresslist [1]实际上可以工作,但是由于我不知道可能有多少个地址,不幸的是我不能仅将X地址存储为单独的变量并复制该函数。

The error I get when running my code is: 运行代码时出现的错误是:

'TypeError: expected str, bytes or os.PathLike object, not list' “ TypeError:预期的str,字节或os.PathLike对象,而不是列表”

Finally, I've tested with a hardcoded list of addresses just to rule out an issue with how the list is being extracted from the database, eg: 最后,我用硬编码的地址列表进行了测试,目的是排除列表如何从数据库中提取的问题,例如:

addresslist = ['C:\\Subfolder1\\Subfolder2', 'D:\\Subfolder1\\Subfolder2']

and, because of unpacking errors: 并且,由于解包错误:

x,y = ['C:\\Subfolder1\\Subfolder2', 'D:\\Subfolder1\\Subfolder2']

Thanks 谢谢

Your first for loop doesn't do what you want it to. 您的第一个for循环不会执行您想要的操作。 It's close, but not quite. 距离很近,但不完全是。

for root, dirs, files in chain.from_iterable(os.walk(addresslist[0:], topdown=False) for path in (str(addresslist[0:])))

What your loop is currently doing is converting your addresslist into a string. 您的循环当前正在执行的操作是将addresslist转换为字符串。 Then you are actually iterating over each character in that string which is put into the path variable. 然后,您实际上是遍历放置在path变量中的字符串中的每个字符。 Then you are trying to chain a series of os.walk generators. 然后,您尝试链接一系列os.walk生成器。 But os.walk needs a single path. 但是os.walk需要一条路径。 You also aren't using that path variable anywhere else in your code. 您也不会在代码的其他任何地方使用该path变量。

This should be: 应该是:

for path in addresslist:
   # it looks like you are worried that not all paths will be strings
   # if that's really a concern, then leave this next line.
   # Otherwise, I think it is safe to delete it
   path = str(path) 
   for root, dirs, files in os.walk(path, topdown=False):

That will take each element from addresslist (which is the path you want to search) and do an os.walk over it. 这将从addresslist获取每个元素(这是您要搜索的路径),并对其进行os.walk I don't think you need to be using chain here at all. 我认为您根本不需要在这里使用chain

If you want to use chain (which isn't necessary) you can follow the outline provided by this SO post: os.walk multiple directories at once . 如果要使用chain (不必要),则可以遵循此SO帖子提供的概述: os。一次遍历多个目录

for root, dirs, files in chain.from_iterable(os.walk(str(path)) for path in addresslist):

One more thing that you should do is have addresslist be a parameter that is passed into your function. 您应该做的另一件事是让addresslist成为传递给函数的参数。

def FileDeleter(addresslist):
   # your function code here
# then you need to actually call the function
addresses = get_locations()
FileDeleter(addresses)

Relying on global variables can get you in a lot of trouble as your code becomes more complex. 随着代码变得更加复杂,依赖全局变量会给您带来很多麻烦。

I've got this working now and wanted to confirm what I did. 我现在已经开始工作了,想确认一下我做了什么。

There were two issues. 有两个问题。 I needed the additional for loop suggested by @TheF1rstPancake and @Michael Butscher. 我需要@ TheF1rstPancake和@Michael Butscher建议的附加for循环。

The second problem was extracting the list of directories from the database. 第二个问题是从数据库中提取目录列表。

def get_location():
    c.execute('SELECT ADDRESS FROM DIRECTORY')
    data = c.fetchall()
    SQLlist = [row for row in data]
    return SQLlist

I was using the above but found when you print(data) you got a tuple of tuples or list of tuples which it was failing to loop through for os.walk to use. 我在使用上面的方法,但是发现当您打印(数据)时,您得到了一个元组元组或元组列表,但这些元组无法循环通过以供os.walk使用。 The result looked like 结果看起来像

[('C:\\Subfolder1\\Subfolder2',), ('D:\\Subfolder1\\Subfolder2',)]

The solution I used is below 我使用的解决方案如下

def get_location():
    c.execute('SELECT ADDRESS FROM DIRECTORY')
    data = c.fetchall()
    SQLlist = []
    for row in range(len(data)):
        SQLlist.append(data[row][0])
    return SQLlist

This now gives me the list: 现在,这给了我列表:

['C:\\Subfolder1\\Subfolder2', 'D:\\Subfolder1\\Subfolder2']

When running this list through the additional for loop os.walk now correctly searches all the directories. 通过附加的for循环运行此列表时,os.walk现在可以正确搜索所有目录。

Thanks for everyone's help, really appreciate this! 感谢大家的帮助,非常感谢!

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM