Open up PowerShell ISE and try running this:
$targets = @()
$folders = dir "D:\Users\Forza\Music\" | Where {$_.mode -match "d"}
foreach ($folder in $folders) {
if(
($folder.GetFiles() |
Measure-Object |
Select -ExpandProperty Count) -eq 1)
{$targets += $folder}
}
$targets | Format-Table -Property Name
This (should) kick out a list of all folders with a single file in them. Take a good look at the list and make sure there's no unintended folders. Then you can run the command:
foreach ($target in $targets){Remove-Item -Recurse -Force $target.FullName}
This will delete all the folders that were listed in $targets
.
If you need to modify this script, it helps to understand what it's doing. For example, as-is you would be deleting any folders with subfolders but no files in the first directory. So if you have something like C:\Users\Forza\Music\SomeArtist\SomeAlbum
, the entire directory SomeArtist
would be deleted. Also, any empty folders will remain.
Let's go line-by-line:
$targets = @()
defines an array. This is so we can add $folder
s to $targets
without throwing an error and make sure that $targets
starts out empty, rather than continually adding to it while modifying our script and eventually deleting far more folders than we intended.
$folders = dir 'C:\Users\Forza\Music\' | Where {$_.mode -match "d"}
lists the contents of the specified directory and pipes that output to the Where-Object
command. $_.mode -match "d"
takes the piped objects and checks that they are directories.
foreach ($folder in $folders) {
start looping through each folder
if(
begins an if statement to check file count inside the folder. I've split each line to make it confusing readable.
$folder.GetFiles() |
this grabs all the files in the folder we're checking. Notice the pipe, which sends the output to the next command on the next line.
Measure-Object |
is pretty self explanatory. If not, try the command Get-Help Measure-Object
.
Select -ExpandProperty Count) -eq 1)
selects and expands the Count
property so we can see if it equals (-eq
) 1. Notice the two closing parenthesis, one to close ($folder.GetFiles() | Measure-Object | Select -ExpandProperty Count)
and one to close the if
statement.
{$targets += $folder}
adds our criteria-matching folder to our $targets
list.
}
closes the foreach loop.
$targets | Format-Table -Property Name
kicks out the list of folders for deletion.
If you wanted to modify this to delete empty folders as well, simply change -eq 1
to -lt 2
. With a little creativity you should be able to get the script to handle your messy file structure however you see fit.
To take care of an Artists folder under \Music, change the path to something like C:\Users\Forza\Music\*\*\
.