[ale] THANKS to all who replied to "ls -rt | rm -i" problem, BUT...ATTN:JoeKnapka

Björn Gustafsson bg-ale at bjorng.net
Sun Mar 19 14:10:01 EST 2006


On 3/19/06, Geoffrey <esoteric at 3times25.net> wrote:
> Paul Cartwright wrote:
> > On Sun March 19 2006 7:54 am, Geoffrey wrote:
> >
> >> awk is the toy you want:
> >>
> >> rm -i $(ls -l | awk '/Mar 15/ {print $NF})
>
> Well, I've played around with it a bit, but it's a bit uglier then I
> expected.  There's no easy way to escape the spaces in a file name with
> awk in such a way that 'rm -i' will be happy.
[snip]
>
> Problem is, 'rm -i' sees the filename as two different files when passed
> as in 'rm -i $(...)'
>
> I can pipe the output of the script to xargs, but xargs doesn't wait for
> a response to rm -i, thus that doesn't work either.

The trick is to use eval. If you change your awk script slightly:

ls -l |awk '/Mar 15/ {
    if (NF == 9) { print $NF }
    else {
        for (i=9; i<=(NF - 1); i++) {
            printf "\"%s ", $i; } printf "%s\"\n", $NF; # note quotes
at start and end of filename
    }
}'

and then run rm like this:

eval rm -i $(awkScriptNameHere)

you'll be able to remove those annoying spacey filenames.  At least
that works with bash; I didn't try it with other bourne-type shells. 
Note that this will still fail if you somehow get tabs or newlines (or
other weird $IFS characters you might have) in your filenames, as the
awk script makes an assumption that only (single) spaces are used as
field separators.

A simpler approach that's pretty well guaranteed to work (unless you
have newlines or double-quotes in your filenames) is to use sed:

eval rm -i $(ls -l|sed -n -e 's/$/"/' -e 's/.* Mar 15 [^ ]* /"/p')

The order of the two sed expressions is important, as you only want to
print the lines that match the date string in the second one.



More information about the Ale mailing list