What does ${i%.*} do in this context?

636 views Asked by At

I'm learning a bit about running a bash script in a linux terminal, specifically in the context of converting audio video files.

I came across this command here on SO that does exactly what I want. However, I'd like to understand it better:

for i in *.avi; do ffmpeg -i "$i" "${i%.*}.mp4"; done

Now, this is obviously a for-loop and I get the first * wildcard. I get the do block. But what I don't quite understand is ${i%.*}. Specifically, what does the %.* bit do in the output location? Why not use ${i}.mp4 instead?

2

There are 2 answers

1
ceremcem On BEST ANSWER

It's called parameter expansion and it removes everything starting from the last dot (ie. extension). Try the following:

$ i="foo.bar.baz"
$ echo ${i%.*}
foo.bar

Author of the original code ("${i%.*}.mp4") apparently wanted to replace original extension with .mp4 so the original extension is removed and .mp4 is appended.

0
alex_noname On

Parameter expansion

${parameter%word}

${parameter%%word}

The word is expanded to produce a pattern and matched according to the rules described below (see Pattern Matching). If the pattern matches a trailing portion of the expanded value of parameter, then the result of the expansion is the value of parameter with the shortest matching pattern (the ‘%’ case) or the longest matching pattern (the ‘%%’ case) deleted.