简体   繁体   中英

bash: mv within for loop just recites usage

Let's say I am trying to move files from the form "aa -- bb.pdf" to "bb -- aa.pdf".

The obvious way to do it is this:

for f in *;
do 
mv $f $(echo "$f" | sed -E 's/(.\*) -- (.\*)(\..\*)/\2 -- \1\3/'); 
done

I'd need to add single quotes around some of the arguments, since there are spaces inside the various arguments which wouldn't get picked up correctly, so it should actually look a little more like this:

for f in *; 
do 
    $(echo mv "'"$f"'" "'"$(echo "$f" | sed -E 's/(.\*) -- (.\*)(\..\*)/\2 -- \1\3/')"'");
done

But any way I do this, all I get is the standard usage recital for mv: usage: mv [-f | -i | -n] [-v] source target mv [-f | -i | -n] [-v] source target mv [-f | -i | -n] [-v] source target etc.

When I output this to the screen, it looks great:

mv 'aa -- bb.pdf' 'bb -- aa.pdf'

But no matter what variation I try on this, it just recites usage (presumably telling me something is wrong with my syntax), and I can't figure out why.

Any ideas?

Here is a bash implementation:

re="(.+) -- (.+)([.].+)"
for f in *; do
    if [[ $f =~ $re ]]; then 
        newf="${BASH_REMATCH[2]} -- ${BASH_REMATCH[1]}${BASH_REMATCH[3]}"
        mv -- "$f" "$newf"
    fi
done

The reason for your error is likely the -- which tells mv "end of options". Adding an additional -- prior to the filenames should resolve the issue.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM