Author |
Message |
Nei #1 / 16
|
 rm Non-Matching string
I have a directory containing a number of file ($1 & $1.tmp). I nned to remove all the non tmp files. Is there a way to remove files that don't match a given string? I don't think rm has such a flag.
|
Sun, 25 Mar 2007 21:42:20 GMT |
|
 |
Robert Bono #2 / 16
|
 rm Non-Matching string
In article <caef6318.0410060542.4a53a...@posting.google.com>,
crude, but effective: rm `ls ./* |grep -v .tmp` There's also 'rm -i *', and answer 'n' to any '*.tmp' files. <grin>
|
Sun, 25 Mar 2007 22:05:43 GMT |
|
 |
Stephane CHAZELA #3 / 16
|
 rm Non-Matching string
2004-10-6, 06:42(-07), Neil:
If you're using zsh, I would recommand that you use it's extended globbing: setopt extendedglob # to put in your ~/.zshrc Then, simply do: rm ./^*.tmp If you're using ksh, you can do rm ./!(*.tmp) If you're using bash, you could do the same after a shopt -s extglob, and with zsh after setopt kshglob If not, you can do: find . \! -name '.' -prune \! -name '.*' \! -name '*.tmp' \ -exec rm {} \; -- Stephane
|
Sun, 25 Mar 2007 23:53:56 GMT |
|
 |
Stephane CHAZELA #4 / 16
|
 rm Non-Matching string
2004-10-06, 14:05(+00), Robert Bonomi:
[...] You need the -d option of ls. It will remove files that don't have "tmp" in their name (the "." matches any character, so is useless here). There will also be problems with filenames with SPC, TAB, NL, *, ?, [, \ characters. -- Steph
|
Mon, 26 Mar 2007 00:04:22 GMT |
|
 |
Paul Ja #5 / 16
|
 rm Non-Matching string
for i in ./*; do case $i in *.tmp) :;; *) rm "$i";; esac done Or, to build a list of files and remove them all at once: shift $# for i in ./*; do case $i in *.tmp) :;; *) set "$i" ${1+"$@"};; esac done if [ "$#" != 0 ]; then rm "$@"; fi These should work in any Bourne-compatible shell. paul
|
Mon, 26 Mar 2007 00:58:50 GMT |
|
 |
Stephane CHAZELA #6 / 16
|
 rm Non-Matching string
2004-10-06, 12:58(-04), Paul Jarc: [...]
[...] Not in zsh in sh or ksh compatibility mode (in sh compatibility mode word splitting and filename generation is forced in ${1+"$@"} case, that's actually not really a bug, but just how the nesting of parameter expansion operators works in zsh). The common work around for this is to use: case ${ZSH_VERSION+z} in z) alias -g '${1+"$@"}' '"$@"';; esac Or you can stick to POSIX conformance and use "$@". Note that if there's no file in the current directory, you'll get an error from "rm" saying that it can't remove a file named "*". -- Stephane
|
Mon, 26 Mar 2007 01:19:39 GMT |
|
 |
Paul Ja #7 / 16
|
 rm Non-Matching string
If "compatibility mode" isn't actually compatible, I don't see how that can be anything but a bug. The mode exists for no other reason than to produce the same behavior as sh, and in this case, it fails to do that.
Thanks, I forgot about those bits. paul
|
Mon, 26 Mar 2007 02:50:16 GMT |
|
 |
pantherechare #8 / 16
|
 rm Non-Matching string
You could also use the "find" command like this: find . \( -name '*' -a ! -name '*.tmp' \) -print find . ! -name '*.tmp' -print If the command is ok then just add: -exec rm {} \; at the end of the command find . ! -name '*.tmp' -print -exec rm {} \; Et voila the xxx.tmp files will be gone... I hope that will help you...
|
Mon, 26 Mar 2007 03:48:53 GMT |
|
 |
Stephane CHAZELA #9 / 16
|
 rm Non-Matching string
2004-10-06, 14:50(-04), Paul Jarc:
Well, let's say it's an emulation mode. zsh has a csh, ksh and sh emulation mode. They wont exactly mimic csh, ksh or sh because zsh syntax is very different in some ways. For instance csh mode is more a csh look-a-bit-like mode as zsh is definitely a Bourne-type shell. Note that in other shells, ${1+"$@"} is not always consistent from one shell to another: $ sh -c 'printf "<%s>\n" "${1+"$@"}"' - 'a b' <a> <b> $ ksh -c 'printf "<%s>\n" "${1+"$@"}"' - 'a b' <a> <b> $ bash -c 'printf "<%s>\n" "${1+"$@"}"' - 'a b' <a b> -- Stephane
|
Mon, 26 Mar 2007 14:38:32 GMT |
|
 |
Chris F.A. Johnso #10 / 16
|
 rm Non-Matching string
On 2004-10-07, Stephane CHAZELAS wrote:
It make no sense to quote ${1+"$@"}. I tried this script (in a file and called in the normal manner) with each shell (e.g., pdksh ./xx.sh): set -- "a x" b c for p in ${1+"$@"} do echo "<$p>" done It demonstrated the expected and desired behaviour. The output for bash, ash, zsh, pdksh, ksh93, ksh98, FreeBSD's sh and a Bourne shell (SunOS 4.1) was: <a x> <b> <c> However, when I used "${1+"$@"}" (quoted), ksh (88 and 93) and sh on FreeBSD, produced: <a> <x> <b> <c> -- Chris F.A. Johnson http://cfaj.freeshell.org/shell =================================================================== My code (if any) in this post is copyright 2004, Chris F.A. Johnson and may be copied under the terms of the GNU General Public License
|
Mon, 26 Mar 2007 16:53:53 GMT |
|
 |
rakesh shar #11 / 16
|
 rm Non-Matching string
That's because of your quoting "${1+"$@"}" : sh -c 'printf "<%s>\n" ${1+"$@"}' - 'a b' bash -c 'printf "<%s>\n" ${1+"$@"}' - 'a b' both give consistent results: <a b>
|
Mon, 26 Mar 2007 20:17:59 GMT |
|
 |
rakesh shar #12 / 16
|
 rm Non-Matching string
. .... [snipped] .
this would also try to remove subdirectories in the current directory as you did not qualify '-type f' following '-prune' and also any hidden files ending in .tmp would be removed too. /bin/find . \! -name . -prune -type f \ \! -name '*.tmp' \! -name '.*.tmp' \ -exec rm {} \; for file in ./* ./.*;do case $file in *.tmp) :;; *) [ -f "$file" ] && [ ! -L "$file" ] && rm "$file";; esac done
|
Tue, 27 Mar 2007 03:25:13 GMT |
|
 |
Robert Bono #13 / 16
|
 rm Non-Matching string
In article <slrncm85s6.27k.stephane.chaze...@spam.is.invalid>, Stephane CHAZELAS <this.addr...@is.invalid> wrote:
Bzzzzt! Thank you for playing. '.' is *NOT* a wild-card character in file-name globbing.
|
Tue, 27 Mar 2007 03:37:29 GMT |
|
 |
Paul Ja #14 / 16
|
 rm Non-Matching string
But it is special to grep. You probably meant: grep -v '\.tmp' But that still leaves the other problems Stephane mentioned. paul
|
Tue, 27 Mar 2007 04:36:46 GMT |
|
 |
Stephane CHAZELA #15 / 16
|
 rm Non-Matching string
2004-10-7, 12:25(-07), rakesh sharma: [...]
[...] Agreed for the directories. Then, you can add either "-f" (to ignore the errors) or -rf to actually remove the dirs to rm. But .foo.tmp wouldn't be removed because of the \! -name '.*' (added to avoid removing dotfiles, as in the other shell globbing solutions I provided in the part you snipped).
With that one and with a POSIX conformant find, dot files not ending in .tmp would be removed. And with a non-POSIX conformant find such as GNU find, a file named ".tmp" would be removed. Also, it doesn't remove non-regular files. -- Stephane
|
Tue, 27 Mar 2007 14:27:07 GMT |
|
 |
|