A POSIX compliant shell shall provide mechanisms like this to iterate over collections of strings:
for x in $(seq 1 5); do
echo $x
done
But, how do I iterate over each character of a word?
A POSIX compliant shell shall provide mechanisms like this to iterate over collections of strings:
for x in $(seq 1 5); do
echo $x
done
But, how do I iterate over each character of a word?
It's a little circuitous, but I think this'll work in any posix-compliant shell. I've tried it in dash
, but I don't have busybox handy to test with.
var='ab * cd'
tmp="$var" # The loop will consume the variable, so make a temp copy first
while [ -n "$tmp" ]; do
rest="${tmp#?}" # All but the first character of the string
first="${tmp%"$rest"}" # Remove $rest, and you're left with the first character
echo "$first"
tmp="$rest"
done
Output:
a
b
*
c
d
Note that the double-quotes around the right-hand side of assignments are not needed; I just prefer to use double-quotes around all expansions rather than trying to keep track of where it's safe to leave them off. On the other hand, the double-quotes in [ -n "$tmp" ]
are absolutely necessary, and the inner double-quotes in first="${tmp%"$rest"}"
are needed if the string contains "*".
You can use the fold
command to add a newline after each character and store the result on a variable. You can then iterate over its elements.
word="some_word"
word=$(echo "$word" | fold -w 1)
for x in "$word"; do
echo $x
done
It will print:
s
o
m
e
_
w
o
r
d
This works in dash
and busybox
:
echo 'ab * cd' | grep -o .
Output:
a
b
*
c
d