[Tfug] rereading stdin
Claude Rubinson
rubinson at u.arizona.edu
Fri Feb 17 20:32:15 MST 2006
Okay. Right. Haven't made much use of file descriptors and it didn't
even occur to me. But I think that's exactly the right solution.
Thanks.
C.
On Fri, Feb 17, 2006 at 08:07:26PM -0700, Stephen Hooper wrote:
> Claude Rubinson wrote:
> >I'm wondering how people handle situations in which they need to step
> >through stdin more than once. As an example, lets say that I want to
> >compute some deviation statistics: x - mean(x). The formula requires
> >that I step through the input twice, once to compute mean(x) and once
> >to compute x - mean(x) for every x.
> >
> >If I'm working in a higher-level language (such as Python), this isn't
> >an issue as I'll have already read the input into an object of some
> >sort. Where it rears its head is when I'm working in shell (as is my
> >preference). I can read the input into variables (or, more likely,
> >arrays) or write it first to a temp file (possibly using tee). I tend
> >to prefer the second solution (with tee) but both feel kludgey to me.
> >
> >Thoughts?
> >
>
> If you are using Bourne shell:
>
> <pre>
> #!/bin/sh
>
> # Get a tempfile
> tmpfile=$(mktemp -p /tmp fooXXXXXXX) || exit 1
>
> # Open up some fd's to it
>
>
> # Fancier shells may allow you to "rewind"
> # a file descriptor. I don't think POSIX
> # does, but as bash can write sockets,
> # I wouldn't be surprised if it couldn't
> # do most anything.
>
> exec 10>${tmpfile}
> exec 11<${tmpfile}
> exec 12<${tmpfile}
>
> # Remove the file so that if something dies
> # we don't have to worry about cleaning it up
> rm ${tmpfile}
>
> # Put stdin into it
> cat >&10 # We opened 10 so that in case "cat" died, the tempfile would
> still be dissappeared. In the case of "cat" this is probably a little
> silly.
>
> # Read stdin from the file
> (
> read line
> while [ $? -eq 0 ] ; do
> echo "My super line: ${line}"
> read line
> done
> ) <&11
>
> # Read stding from the file
> (
> read line
> while [ $? -eq 0 ] ; do
> echo "My second super line: ${line}"
> read line
> done
> ) <&12
>
> </pre>
>
> The limitations are that you need space to equal the amount you are reading
> in, and that you end up opening an fd for each time you want to read the
> data in (as there is no rewind).
> _______________________________________________
> tfug mailing list
> tfug at tfug.org
> http://www.tfug.org/mailman/listinfo/tfug
More information about the tfug
mailing list