Reputation: 3792
I've tried several iterations of a script but now back to staring at a blank Notepad++
I have 6k folders in the form:
Reading Festival 1999
Reading Festival 2000
Reading Festival 2001
Leeds Festival 1999
Leeds Festival 2000
Leeds Festival 2001
Download Festival 2005
Download Festival 2006
...
In the same folder I have a long list of files in the form
Artist at {Festival Name} by Photographer - UID
Where Artist
is someone who played at the festival, Photographer
is the person who took it and UID
is a unique ID
My question is how would I go about looping through the folders, for each, see if a filename contains the name of the folder, if it does, move the file there.
import os
rootdir = 'C:\Users\Alan\Desktop\VF'
for subdir, dirs, files in os.walk(rootdir):
for d in dirs:
for file in files:
the_file = os.path.join(subdir, file)
if d in the_file:
new_loc = subdir + '\\' + d + '\\' + file
os.rename(the_file, new_loc)
I have this code which I believe should work but my worry is that it will read through all the images already within folders. How would I avoid this?
Upvotes: 2
Views: 1303
Reputation: 197
Since your files and folders are on the same level, you don't need to use os.walk()
to traverse the directory tree. os.listdir()
will do instead, as you noted in the comments. One solution would be to get the directory and file lists with os.listdir()
and find the new_loc
name in the same way you did before, using in
instead of regex.
folders = [d for d in os.listdir('.') if os.path.isdir(d)]
files = [f for f in os.listdir('.') if os.path.isfile(f)]
for d in folders:
for f in files:
if d in f:
new_loc = subdir + '\\' + d + '\\' + file
os.rename(the_file, new_loc)
The logic here is about the same as yours, just with a different way of getting your directories and files!
Upvotes: 1
Reputation: 1824
If I'm understanding properly, you have a top level directory and when you start this process, everything in it is either an empty directory corresponding to a festival or a file to be moved. I don't think you need to use os.walk
at all, just iterate through what's in the top level directory.
I'll assume you have two functions defined:
def extract_festival(fname)
returning "Reading Festival 1999" or whatever is appropriatedef move_file(fname, festival)
to move the file into place. You'll need to check whether the festival's directory exists and if not do whatever's appropriate.Then you just need something like:
for fname in os.listdir(rootdir):
if os.path.isfile(os.path.join(rootdir, fname)): # double check that listdir doesn't give you the full path
festival = extract_festival(fname)
move_file(fname, festival)
# otherwise, it's a directory, so leave it alone
I do think that extract_festival
is a regex. Something like this will handle the "happy" case:
def extract_festival(fname):
match = re.match(".+at(.+[0-9]{4}) by.+")
return match.group(1)
If you fail to match (e.g. if you have a bad file name), match
will be None
and you'll have to decide what to do. The match.group
will throw an error in that case. I'd probably do something like return match.group(1) if match is not None else match
and then check for None
up in the for loop (and probably print the filename so I could go fix it by hand).
Upvotes: 0