I found this example on SO, titled: Terminal - Delete All Folders Not Conatining .mp3 Files.
#! /bin/bash
find -depth -type d | while read -r D
do
v=$(find "$D" -iname '*.mp3')
case "$v" in
"" )
echo "$D no mp3"
# rm -fr "$D" #uncomment to use
;;
esac
done
Example
Sample data.
.
|-- 1
| |-- 1.mp3
| `-- 1.txt
|-- 2
| `-- 2.mp3
|-- 3
| `-- 3.txt
|-- 4
| `-- 4.txt
|-- 5
| `-- 5.mp3
|-- 6
| `-- 61
| `-- 61.mp3
|-- 7
| `-- 71
| `-- 71.txt
`-- deletenomp3.bash
Sample run
If I were to run it it would delete the following:
$ ./deletenomp3.bash
./7 no mp3
./7/71 no mp3
./4 no mp3
./3 no mp3
Other file types
You can simply extend this by adding more -name
arguments to the 2nd find command in the script. Example, to add .wav
files:
v=$(find "$D" -iname '*.mp3' -o -iname '*.wav');
That says *.mp3
OR *.wav
. To add more or others:
v=$(find "$D" -iname '*.mp3' -o -iname '*.flac' -o -iname '*.m4a');
I'm sure this block could be condensed if you had a lot more file types using alternative switching to find
.
The tool to display inode detail for a filesystem will be filesystem specific. For the ext2
, ext3
, ext4
filesystems (the most common Linux filesystems), you can use debugfs
, for XFS xfs_db
, for ZFS zdb
. For btrfs
some information is available using the btrfs
command.
For example, to explore a directory on an ext4
filesystem (in this case /
is dev/sda1
):
# ls src
Animation.js Map.js MarkerCluster.js ScriptsUtil.js
Directions.js MapTypeId.js markerclusterer.js TravelMode.js
library.js MapUtils.js Polygon.js UnitSystem.js
loadScripts.js Marker.js Polyline.js Waypoint.js
# ls -lid src
664488 drwxrwxrwx 2 vagrant vagrant 4096 Jul 15 13:24 src
# debugfs /dev/sda1
debugfs: imap <664488>
Inode 664488 is part of block group 81
located at block 2622042, offset 0x0700
debugfs: dump src src.out
debugfs: quit
# od -c src.out
0000000 250 # \n \0 \f \0 001 002 . \0 \0 \0 204 030 \n \0
0000020 \f \0 002 002 . . \0 \0 251 # \n \0 024 \0 \f 001
0000040 A n i m a t i o n . j s 252 # \n \0
0000060 030 \0 \r 001 D i r e c t i o n s . j
0000100 s \0 \0 \0 253 # \n \0 024 \0 \n 001 l i b r
0000120 a r y . j s \0 \0 254 # \n \0 030 \0 016 001
0000140 l o a d S c r i p t s . j s \0 \0
0000160 255 # \n \0 020 \0 006 001 M a p . j s \0 \0
0000200 256 # \n \0 024 \0 \f 001 M a p T y p e I
0000220 d . j s 257 # \n \0 024 \0 \v 001 M a p U
0000240 t i l s . j s \0 260 # \n \0 024 \0 \t 001
0000260 M a r k e r . j s \0 \0 \0 261 # \n \0
0000300 030 \0 020 001 M a r k e r C l u s t e
0000320 r . j s 262 # \n \0 034 \0 022 001 m a r k
0000340 e r c l u s t e r e r . j s \0 \0
0000360 263 # \n \0 024 \0 \n 001 P o l y g o n .
0000400 j s \0 \0 264 # \n \0 024 \0 \v 001 P o l y
0000420 l i n e . j s \0 265 # \n \0 030 \0 016 001
0000440 S c r i p t s U t i l . j s \0 \0
0000460 266 # \n \0 030 \0 \r 001 T r a v e l M o
0000500 d e . j s \0 \0 \0 267 # \n \0 030 \0 \r 001
0000520 U n i t S y s t e m . j s \0 \0 \0
0000540 270 # \n \0 240 016 \v 001 W a y p o i n t
0000560 . j s \0 305 031 \n \0 214 016 022 001 . U n i
0000600 t S y s t e m . j s . s w p \0 \0
0000620 312 031 \n \0 p 016 022 001 . U n i t S y s
0000640 t e m . j s . s w x \0 \0 \0 \0 \0 \0
0000660 \0 \0 \0 \0 \0 \0 \0 \0 \0 \0 \0 \0 \0 \0 \0 \0
In the above, we start by finding the inode of directory src
(664488
) and then dump its contents into file src.out
and then display that using od
. As you can see, the contents of all of the files in that directory (Animation.js
, etc.) are visible in the dump.
This is just a start - see the debugfs
manual page or type help
within debugfs
for more information.
If you're using ext4
, you can find more information about the structure and layout of directory entries in the kernel documentation.
Best Answer
On a
gnu
setup you could run:Alternatively, with
zsh
, you could try something like this:It extracts the numbers (the first three digits) from each file name, sorts them and saves the result in an array -
myarr
. It then sets another array -mynums
containing numbers from001
up to the value of the last index (i.e. the highest number extracted from the file names) and then uses parameter expansion to remove the values inmyarr
from the expansion ofmynums
.