print a variable out side of while read line in solaris
I write following code to update all packages in "total" variable and i will use this variable later. But i am not getting "total" value out side of loop. Please help me to solve this problem
#!/bin/sh name=`pkginfo -i` echo "$name" | while read LINE do n=`echo $LINE|awk '{print $2}'` echo $n total="$total $n" done echo $total ThanQ, Nagendra |
Use the korn shell.
The bourne shell (and bash for that matter) do not preserve the "total" variable set in your pipeline. Code:
#!/bin/ksh |
Please use ***[code][/code]*** tags around your code and data, to preserve the original formatting and to improve readability. Do not use quote tags, bolding, colors, "start/end" lines, or other creative techniques.
As stated, bash and most other sh-style shells run piped commands in subshells. This means any environment settings made in them are lost when the loop terminates. ksh, however, runs the final entry in the pipe chain in the main shell, and so this does work properly in it. I set variables in a loop that's in a pipeline. Why do they disappear after the loop terminates? Or, why can't I pipe data to read? http://mywiki.wooledge.org/BashFAQ/024 Note that bash has recently introduced a lastpipe shell option that does the same thing, but it conflicts with job management and so isn't enabled by default. It's also not recommended for interactive use because of this. For all sh-based shells (including ksh), you can usually use some form of redirection for input instead. Code:
while read line; do Now to give you some other script pointers (links are for bash, but the general advice is applicable to all shells). 1) When you use "!#/bin/sh" as the shebang, your script will be interpreted according to POSIX compatibility, and the use of shell-specific features becomes questionable at best. This is usually not what you want, so always be sure to explicitly state the interpreter you want to use (e.g. /bin/bash or /bin/ksh ). 2) $(..) is highly recommended over `..`. Please try to avoid using backticks. This is posix-defined and fully portable for all but the oldest shells. 3) Lists of things should never be stored in a single scalar variable, except in the case of limited, POSIX-based shells. Always use arrays if the shell supports them, or process the input directly. I assume that "pkginfo -i" produces such a list. If the shell doesn't support arrays then you have to be much more careful in how you handle such things. See the next point for why: 4) QUOTE ALL OF YOUR VARIABLE EXPANSIONS. You should never leave the quotes off a parameter expansion unless you explicitly want the resulting string to be word-split by the shell and possible globbing patterns expanded. This is a vitally important concept in scripting, so train yourself to do it correctly now. You can learn about the exceptions later. http://mywiki.wooledge.org/Arguments http://mywiki.wooledge.org/WordSplitting http://mywiki.wooledge.org/Quotes (You're actually mostly ok here. You just missed one set, in front of the awk command.) 5) A small point: since environment variables are generally all upper-case, it's recommended practice to keep your own user variables in lower-case or mixed-case to help differentiate them. 6) You don't need awk to split a line if you know how to use read properly. Speaking of which, always use the "-r" option, to keep backslashes in the input from being interpreted. Code:
#!/bin/ksh Code:
#!/bin/ksh How can I read a file (data stream, variable) line-by-line (and/or field-by-field)? http://mywiki.wooledge.org/BashFAQ/001 How can I use array variables? http://mywiki.wooledge.org/BashFAQ/005/ string manipulations in bash. Most of them are portable to ksh. |
Thanks David the H. for your detailed and insightful reply.
Just a small comment about this statement: Quote:
POSIX actually recommend not to use any shebang at all for a compatible script to run in a POSIX environment. Under Solaris, this environment is met by having /usr/xpg4/bin first in the PATH variable. |
All times are GMT -5. The time now is 07:05 PM. |