Is it possible to loop over tuples in bash?
As an example, it would be great if the following worked:
for (i,j) in ((c,3), (e,5)); do echo \"$i and $
$ echo 'c,3;e,5;' | while IFS=',' read -d';' i j; do echo "$i and $j"; done
c and 3
e and 5
Using printf
in a process substitution:
while read -r k v; do
echo "Key $k has value: $v"
done < <(printf '%s\n' 'key1 val1' 'key2 val2' 'key3 val3')
Key key1 has value: val1
Key key2 has value: val2
Key key3 has value: val3
Above requires bash
. If bash
is not being used then use simple pipeline:
printf '%s\n' 'key1 val1' 'key2 val2' 'key3 val3' |
while read -r k v; do echo "Key $k has value: $v"; done
$ for i in c,3 e,5; do IFS=","; set -- $i; echo $1 and $2; done
c and 3
e and 5
About this use of set
(from man builtins
):
Any arguments remaining after option processing are treated as values for the positional parameters and are assigned, in order, to $1, $2, ... $n
The IFS=","
sets the field separator so every $i
gets segmented into $1
and $2
correctly.
Via this blog.
Edit: more correct version, as suggested by @SLACEDIAMOND:
$ OLDIFS=$IFS; IFS=','; for i in c,3 e,5; do set -- $i; echo $1 and $2; done; IFS=$OLDIFS
c and 3
e and 5
In cases where my tuple definitions are more complex, I prefer to have them in a heredoc:
while IFS=", " read -ra arr; do
echo "${arr[0]} and ${arr[1]}"
done <<EOM
c, 3
e, 5
EOM
This combines looping over lines of a heredoc with splitting the lines at some desired separating character.
do echo $key $value
done < file_discriptor
for example:
$ while read key value; do echo $key $value ;done <<EOF
> c 3
> e 5
> EOF
c 3
e 5
$ echo -e 'c 3\ne 5' > file
$ while read key value; do echo $key $value ;done <file
c 3
e 5
$ echo -e 'c,3\ne,5' > file
$ while IFS=, read key value; do echo $key $value ;done <file
c 3
e 5
Based on the answer given by @eduardo-ivanec without setting/resetting the IFS
, one could simply do:
for i in "c 3" "e 5"
do
set -- $i
echo $1 and $2
done
The output:
c and 3
e and 5