Shell tips and tricks
VirginSnow at vfemail.net
VirginSnow at vfemail.net
Thu Nov 1 15:26:02 EDT 2007
> Date: Thu, 1 Nov 2007 13:09:00 -0400
> From: "Ben Scott" <dragonhawk at gmail.com>
> Sheesh. That makes even less sense to me. Let me see if I have
> this right. Two examples:
>
> foo | while read LINE ; do bar ; i=$(( i + 1 )) ; done
>
> while read LINE ; do bar ; i=$(( i + 1 )) ; done < <(foo)
>
> The first results in the "do clause" being run in a subshell, while
> the second does not? Why is that? In both cases, we're sending
> output from one process into the shell's internal "read" builtin. Is
> there any rhyme or reason to this?
It's because the former example uses the itsy bitsy oh-so-narrow
who-ever-woulda-thought such-a-small-character could-cause-so-much
trouble "|" character. Using "|" is roughly equivalent to doing a
fork() and hooking file descriptors up so that one process's outputs
go to the other process's inputs. Each time you add "| blah" to a
command, bash automatically forks & shuffles file descriptors.
Compare:
(1)$ x=0 ; /bin/true ; x=1 ; echo "$x"
1
(2)$ x=0 ; /bin/true | x=1 ; echo "$x"
0
This happens because (1) is equivalent to:
{ x=0 ; /bin/true ; x=1 ; echo "$x" ; }
but (2) means:
x=0 ; /bin/true | { x=1 ; } ; echo "$x"
More information about the gnhlug-discuss
mailing list