Unix & Linux Stack Exchange is a question and answer site for users of Linux, FreeBSD and other Un*x-like operating systems. It's 100% free, no registration required.

Sign up
Here's how it works:
  1. Anybody can ask a question
  2. Anybody can answer
  3. The best answers are voted up and rise to the top

I know how to delete all txt file under current directory by rm *.txt. Does anyone know how to delete all files in current directory EXCEPT txt file?

share|improve this question

migrated from stackoverflow.com Jun 5 '13 at 19:48

This question came from our site for professional and enthusiast programmers.

As always, test the given answers with a harmless command like ls before actually attempting to call rm. – chepner Jun 5 '13 at 15:58
up vote 33 down vote accepted

You can use find

find . -type f ! -name '*.txt' -delete

Or bash's extended globbing features

shopt -s extglob
rm *.!(txt)

Or in zsh

rm *~*.txt(.)
#  ||     ^^^ Only plain files
#  ||^^^^^ files ending in ".txt"
#  | \Except
#   \Everything
share|improve this answer
Some of these may need to be adapted depending on whether you have folders and what you want to do with them. – Kevin Jun 5 '13 at 15:58
Shouldn't *.!(txt) be !(*.txt)? – user495470 Jun 6 '13 at 8:32
@LauriRanta depends on what's in the folder, which we haven't gotten an answer to. It's fine as is if all the files have extensions, and rm would choke if there were folders. – Kevin Jun 6 '13 at 13:22
I've got an issue with the brackets. When I use the globbing style in a bash script, it complains about a syntax error and the parentheses. However doing it from the CLI works. – CMCDragonkai Jan 17 '14 at 8:56

there are many ways could do it. but the most simple way would be (bash):

shopt -s extglob
rm !(*.txt)
share|improve this answer

One solution without find:

mv dir/*.txt otherdir/
rm -r /dir
mv otherdir dir

This should work on all kind of shells.

share|improve this answer

If you just want to delete all files except '*.txt' then you can use the following command:

$ find . -type f ! -name "*.txt" -exec rm -rf {} \;

but if you also want to delete directories along with the files then you can use this:

$ find . ! -name "*.txt" -exec rm -r {} \;

share|improve this answer

You can use inverted grep and xargs

ls | grep -v .txt$| xargs rm
share|improve this answer
ls | grep -v *.txt | xargs rm works just as well – phillipsk Feb 27 at 13:32

Your Answer


By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.