Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

linux shell script: split string, put them in an array then loop through them [duplicate]

Tags:

bash

Possible Duplicate:
Split string based on delimiter in Bash?

In a bash script how do I split string with a separator like ; and loop through the resulting array?

like image 776
Funky Dude Avatar asked Sep 10 '09 18:09

Funky Dude


4 Answers

You can probably skip the step of explicitly creating an array...

One trick that I like to use is to set the inter-field separator (IFS) to the delimiter character. This is especially handy for iterating through the space or return delimited results from the stdout of any of a number of unix commands.

Below is an example using semicolons (as you had mentioned in your question):

export IFS=";"
sentence="one;two;three"
for word in $sentence; do
  echo "$word"
done

Note: in regular Bourne-shell scripting setting and exporting the IFS would occur on two separate lines (IFS='x'; export IFS;).

like image 181
user132447 Avatar answered Oct 05 '22 02:10

user132447


If you don't wish to mess with IFS (perhaps for the code within the loop) this might help.

If know that your string will not have whitespace, you can substitute the ';' with a space and use the for/in construct:

#local str
for str in ${STR//;/ } ; do 
   echo "+ \"$str\""
done

But if you might have whitespace, then for this approach you will need to use a temp variable to hold the "rest" like this:

#local str rest
rest=$STR
while [ -n "$rest" ] ; do
   str=${rest%%;*}  # Everything up to the first ';'
   # Trim up to the first ';' -- and handle final case, too.
   [ "$rest" = "${rest/;/}" ] && rest= || rest=${rest#*;}
   echo "+ \"$str\""
done
like image 20
NVRAM Avatar answered Oct 05 '22 03:10

NVRAM


Here's a variation on ashirazi's answer which doesn't rely on $IFS. It does have its own issues which I ouline below.

sentence="one;two;three"
sentence=${sentence//;/$'\n'}  # change the semicolons to white space
for word in $sentence
do
    echo "$word"
done

Here I've used a newline, but you could use a tab "\t" or a space. However, if any of those characters are in the text it will be split there, too. That's the advantage of $IFS - it can not only enable a separator, but disable the default ones. Just make sure you save its value before you change it - as others have suggested.

like image 33
Dennis Williamson Avatar answered Oct 05 '22 02:10

Dennis Williamson


Here is an example code that you may use:

$ STR="String;1;2;3"
$ for EACH in `echo "$STR" | grep -o -e "[^;]*"`; do
    echo "Found: \"$EACH\"";
done

grep -o -e "[^;]*" will select anything that is not ';', therefore spliting the string by ';'.

Hope that help.

like image 35
NawaMan Avatar answered Oct 05 '22 01:10

NawaMan