Bill Gradwohl wrote: > echo ===========Loop 1============== > declare -a RULES > i=0 > j=4 > > # Read the test file line by line into the RULES array. > cat /tmp/junkfile| while read x; do > RULES[i++]="$x" > # Show what RULES contains > echo j=$j i=$i RULES has ${#RULES[*]} elements. ${RULES[*]} > done > echo j=$j i=$i RULES has ${#RULES[*]} elements. ${RULES[*]} > > > echo ===========Loop 2============== > declare -a rules > i=0 > j=4 > > while test $i -lt 3; do > rules[i++]="line $((i+1))" > # Show what rules contains > echo j=$j i=$i rules has ${#rules[*]} elements. ${rules[*]} > done > echo j=$j i=$i rules has ${#rules[*]} elements. ${rules[*]} ...
The first loop appears to stuff the array with values and i is steadily increasing.
Correct, but the while loop is in a different shell than the body of the script that will continue executing. The changes happen within that shell, and are lost when it exits.
After the loop ends, i is 0 and the array is empty.
Anytime you pipe '|' data, the right hand side of the pipe will be executed in a different shell or process than the left hand side.
Why? Since i & j are initialized prior to loop start, and displayed during the loop, why is j's value maintained across the loop and i appears to get reinitialized to the pre loop value?
'j' isn't "maintained". It's never modified by your script. Why would it change? Likewise, 'i' is not modified by the body of the script in the first loop, so its value doesn't change *in the body of the script*. It is only modified in the sub-shell executing the while loop.
The second loop is similar. Again j keeps its value the entire time, and i gets increased steadily. At loop end both j and i are what I would expect them to be.
...Because there's no pipe involved. A pipe always implies that a separate shell or process will be run, and it will not have any side effects on the environment of the script executing it. It will only set the $? variable as a return code.
How are these two loops different? It has to have something to do with the read statement but I can't figure it out.
Note that if you use file redirection instead of a pipe, there is no implied subshell. The while loop executes in the environment of the main script when you pass it the file like:
while read stuff; do ... done < /tmp/file
-- Shrike-list mailing list Shrike-list@xxxxxxxxxx https://www.redhat.com/mailman/listinfo/shrike-list