5

So I am testing the following:

foo() {  
  printf "\nAll the parameters, each on a separate line:\n"  
  printf "param: %s\n" "$@"  
}  

foo The "nicely colored" rainbow  

The output is:

All the parameters:  
param: The
param: nicely colored
param: rainbow

So if I understand correctly because IFS is set to \t\n we get the parameters separated by tab (the first char of IFS).
But why are they printed in separate lines?
Is the printf run for each parameter. I.e. does bash converts this into a for loop?
Also the following (without double quotes) outputs the same result:

printf "param: %s\n" $@

Jim
  • 1,391

1 Answers1

17

What is happening here is that when you pass printf more arguments than it has positional formatting parameters for (%s and other things), it will repeat the format. And it is repeating it on multiple lines because you have \n in your format string. There is nothing special about $@ in this case.

For example:

$ printf 'Foo: %s\n' bar baz
Foo: bar
Foo: baz

$ printf 'Foo: %s %s\n' bar baz
Foo: bar baz
phemmer
  • 71,831
  • yes. maybe add a little explanation of why "$@" is preferred to "$" or other forms, as it is (almost) the only one that "keeps the grouping" of the parameters. (ie : foo 1 "2 3" 4 : the use of "$@" keeps "2 3" together. Is is a bit like if the shell replaces "$@" with "1" "2 3" "4". if you used `"$"intead : the shell replaces it with : "1 2 3 4" (ie, just 1 string with everything inside).$@will be subject to IFS separation (here: 1 2 3 4 ), and$*` as well. – Olivier Dulac Mar 26 '18 at 15:44
  • 5
    If one wants to know the difference between $* and $@, I would recommend seeking the question specifically about that – phemmer Mar 26 '18 at 16:56
  • "positional formatting parameters" is confusing terminology: In shell lingo, the positional parameters are $1, $2, ..., so I'd suggest saying "more arguments than it has conversions in the format string". Although that ignores the fact that the format string itself is an arg, so maybe there's an even better way to phrase it. Maybe "more arguments to print"? Anyway, "conversions" or "conversion specifier" is official printf terminology, and fortunately is clear in English without needing a definition. – Peter Cordes Mar 26 '18 at 23:26