4

In a bash script, I would like to transform a string containing variable separated by ":" into an array.

I see that the proposed approach is usually

IFS=: read -r -a myarray <<< "$mystring"

I used instead a command that looks simpler to me:

IFS=: myarray=($mystring)

Moreover on my PC it works. See the script hereunder

#!/bin/bash

mystring="var01:var02:var03:var04"

IFS=: myarray=($mystring)

echo "first variable is" "${myarray[0]}"
echo "second variable is" "${myarray[1]}"
echo "..."

output is

first variable is var01
second variable is var02
...

However, as I did not found such example on the web, I'm not sure it's correct...

What would be the issue of using this in bash script ? Is it compliant with standard ?

Thanks for your advice.

1 Answer 1

6

Nice first question. Your proposed alternative does have issues. First consider

$ str='a:%:*'
$ IFS=: read -r -a arr <<< "$str"
$ echo "${arr[@]}"
a % *

The result is the expected one. Because "$str" is quoted in a herestring, it does not undergo filename expansion (as known as globbing) and all is quite right.

On the other hand...

$ str='a:%:*'
$ IFS=: arr=($str)
$ echo "${arr[@]}"
a % 07-13:37:38.png 07-13:37:49.png Documents Downloads Pictures Music Xresources

In this second case, $str is unquoted and undergoes filename expansion, which means * is expanded to all files in my current directory! Alas!

None of those forms are POSIX compliant because POSIX does not define arrays in shells. But both are totally valid in Bash, although, as demonstrated, they do different things.

A reference in Bash's manual: Filename Expansion.


As you have noted, you can use set -f to disable filename expansion. That would solve the problem of IFS=: arr=($str), but may surprise some. If going this way, set it back with set +f right after that line or the setting will apply to the whole rest of the script. It increases the complexity of the solution, so I recommend avoiding this whenever possible.

Sign up to request clarification or add additional context in comments.

1 Comment

I read in Bash's manuel "After word splitting, unless the -f option has been set". So, I suppose to avoid this I should first set de option -f but it increase the complexity of solution. I will further look in this but I understand the issue

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.