2

It was an old problem. I knew how to delete files and exclude some, like this:

rm `find ~/temporary/Test\ 1 -mindepth 1 -maxdepth 1|grep -v 'A'`

but the problem is the folder 'Test 1' containing a space in name, the result of find was

/home/owner/temporary/Test 1/B

It makes rm error, how can I fix it?

Kevin Panko
  • 7,346
  • 22
  • 44
  • 53
John
  • 23
  • 1
  • 6
  • Thanks, but my most annoying problem is spaces and other special character are in the file names, those methods can't fix it. And I don't know how to search for this problem :-( – John Nov 22 '13 at 06:35
  • 1
    Don't try to parse the output of `find` or `ls`. They were not meant to have their output parsed, because `find` can work on files directly: http://mywiki.wooledge.org/ParsingLs – slhck Nov 22 '13 at 09:29
  • Okay, maybe I understood. – John Nov 22 '13 at 10:59

2 Answers2

2

This solution works even with spaces but requires some typing:

find -mindepth 1 -maxdepth 1 ! -name "peter" ! -name "paul & mary" -exec rm {} \+

Or with newer find versions (findutils >= 4.2.3):

find -mindepth 1 -maxdepth 1 ! -name "peter" ! -name "paul & mary" -delete
scai
  • 1,032
  • 10
  • 18
  • 1
    The `-print0 | xargs -0` version isn't needed. You can call `-exec rm {} \+` directly, which would be more efficient. – slhck Nov 22 '13 at 09:30
  • @slhck Thanks, I updated my answer. Although the efficiency is questionable because `xargs` would lead to fewer `rm` calls :) – scai Nov 22 '13 at 09:41
  • Thanks scai! It works. When I saw these answers, I realized that they are simple, maybe I need to read more manuals. – John Nov 22 '13 at 10:39
  • I read it twice but somehow I managed to fail to noticed it. Whoops. – Hennes Nov 22 '13 at 12:34
1

Here is my take:

$ mkdir -p temp\ 1/sub\ 1
$ touch temp\ 1/{one,two,three} temp\ 1/sub\ 1/{one,two,three}
$ tree temp\ 1/
temp\ 1/
├── one
├── sub\ 1
│   ├── one
│   ├── three
│   └── two
├── three
└── two

1 directory, 6 files
$ find temp\ 1/ -maxdepth 1 -mindepth 1 -type f ! -regex '.*/.*o.*' -exec rm -v {} \;
removed ‘temp 1/three’

So the key concepts here are:

  1. The -regex filter with negation (! before option) and the pattern that is applied to the whole path of the found file.
  2. The -exec command that has the {} token replaced with properly quoted path. Remember to add the \; to mark the end of the command line.
Rajish
  • 630
  • 2
  • 7
  • 14