I procrastinated to look up this for such a long time.. today was enough. What I want to achieve is reading a line from stdin and split it among several variables, naively I'd do:
$ echo "A BB CCC" | read a b c
$ echo $a $b $c
(no output.) As well explained here the above code doesn't work, but this one does:
$ read a b c < <(echo "A BB CCC")
$ echo $a $b $c
A BB CCC
as a hint, <(cmds) is called process substitution.
Subscribe to:
Post Comments (Atom)
7 comments:
% echo "A BB CCC" | read a b c; echo "$a-$b-$c"
A-BB-CCC
zsh
read a b c <<<"A B C"
gebi: From bash 2.0.5b
now someone has just to find a way how to do this with posix compatible with sh - because there is no process substitution or here documents in posix
josch,
Maybe a quick and dirty perl script with eval' evil :-) magick:
eval $(echo "a b c" | perl -ne '@vars=qw(a b c); s/((?{$a=$vars[$b]; $b=$b+1;})\w+) ?/$a=\1\n/g; print')
Is this posix ?? (I don't know) but it can replace read builtin function (in its basic call, of course)
How about the old trick with set?:
set -- `echo "A BB CCC"`
echo $1 $2 $3
very simple and posix friendly solution:
echo "A BB CCC" | (
read a b c
echo $a $b $c
)
this makes sure read/echo are in the same subshell. alternatively, you could/should use a function:
foo() {
read a b c
echo $a $b $c
}
echo A BB CCC | foo
i'd advise against using set, at least unless you're absolutely sure about your input, since it might not do exactly what you want it to do in some cases.
read a b c <<<"A B C" # is more portable, but also only to modern shells.
echo "A B C" |& read -p a b c # only works on Korn shells, not GNU bash…
Something like this ought to work in POSIX shells:
read a b c <<EOF
A B C
EOF
Feel free to say hi in either #!/bin/mksh (yes that’s a channel name) or #ksh in Freenode IRC.
Post a Comment