views:

45

answers:

3

I rename few files (1234.xml, 9876.xml, 2345.xml etc) with .xml extension with the following code :

 for i in *.xml  
 do  
 mv $i $i.ab  
 done

it becomes 1234.xml.ab, 9876.xml.ab, 2345.xml.ab...etc

Now, I want to rename it to 1234.xml.SD, 9876.xml.SD, 2345.xml.SD...etc.

These are 100 files.

How can this be achieved with the help of code ? Please advise.

A: 

You can do it like that:

for f in *.xml.ab; do
    mv $f `echo $f | sed 's/\.ab$//g'`
done
kogut
ah, cool, much easier :-) thanks !
Ashish
You need double quotes around variable and command substitutions, and `echo` is only reliable if the file name doesn't start with `-` and doesn't contain a backslash. `mv --- "$f" "$(printf %s "$f" | sed 's/\.ab$//g')"` would be ok, but [codaddict's answer](http://stackoverflow.com/questions/4025438/batch-renaming-files-in-unix-and-rollback/4025499#4025499) is both conceptually simpler and easier to get right.
Gilles
+1  A: 

If you are using bash you can do:

for f in *.xml.ab; do
    mv "$f" "${f%.ab}.SD"
done

or just use the rename command as:

rename 's/ab$/SD/' *.xml.ab
codaddict
Thanks, it works for me :-)
Ashish
By d way, it works without "" in the MOVE command.
Ashish
But if your filenames had spaces it would fail without the `"`. So always enclose filenames in `"`.
codaddict
Note that this `rename` command comes from a Perl distribution and is not a standard unix command. Debian (and derived distributions such as Ubuntu) ships it as part of its perl package, but it's unlikely to be available elsewhere.
Gilles
Also, this needs to be `mv -- "$f" "${f%.ab}.SD"` unless you know that file names don't begin with a `-`.
Gilles
@codaddict, ah, valuable tip :-)
Ashish
@Gilles, you mean if the filename starts with -1234.xml.ab, then we should use mv -- "$f" "${f%.ab}.SD" to append it with "SD" ? Is that what you mean ?
Ashish
@Ashish: Yes. Normally, an argument that begins with `-` is an option (or several options). For example here `mv` would consider `1`, `2`, and so on to be options. The argument `--` signals the end of options, so with `mv -- "$f" "${f%.ab}.SD"`, the value of `f` cannot be mistaken for an option. This is not specific to `mv`, most unix commands behave in this way. Therefore `--` is fairly common in well-written scripts (so that the script doesn't misbehave if a file name happens to begin with `-`).
Gilles
@Gilles, thanks for well explained reason :-) Do you advise any good shell-script book which i can refer to :-) That should have well explained basic concepts, important tips, use of regex in scripting, talks about various shells, use of each command and its application :-)
Ashish
@Ashish: No, sorry, I learnt by example and spec-reading, but I'd be incapable of explaining how to tell the good examples from the bad (shell scripting is full of pitfalls like the ones you've seen here). There are a couple of threads on the topic on SO.
Gilles
A: 

I'm not clear if you want to rename foo.xml.ab -> foo.xml or foo.xml.ab -> foo.xml.SD

foo.xml.ab -> foo.xml

for f in *.xml.ab; do
    mv "$f" "${f%.ab}"
done

foo.xml.ab -> foo.xml.SD

for f in *.xml.ab; do
    mv "$f" "${f/.ab/.SD}"
done
JohnCC
@John, it the second code that you wrote [foo.xml.ab -> foo.xml.SD] im trying :-) Thanks
Ashish