When I run the following script with some arguments like arg1 arg2 arg3
:
#!/bin/bash
zenity --entry --text="$@"
zenity creates an entry dialog with this text: "arg1" whereas I expect "arg1 arg2 arg3"
If I use a variable like the following script it shows all arguments for the entry text.
#!/bin/bash
text="$@"
zenity --entry --text="$text"
What's the difference between these scripts? Why does the first one replace $@
with the first argument only?
Best Answer
$@
expands to separate words (whereas$*
expands to a single word), as explained in thebash
manual. Thus, when you writeit expands to
However, shell variable assignments do not undergo word splitting. Note that field / word splitting is omitted in the list of expansions for variable assignments in the
bash
manual. This behavior is consistent with the POSIX spec. So, when you writethe variable
text
gets all of the positional parameters as a single word, equivalent to if you had writtentext="$*"
. Indeed, this is the reason double quotes are often unnecessary in variable assignments. Bothand
are perfectly safe.
So,
expands
"$text"
to a single word, which is why this works. Note that the--option="$@"
is just a normal argument to the commandzenity
, and not a shell variable assignment, which is why word splitting takes place here but not intext=$@
.