title: Using bc as daemon in BASH shell from awk
body: <pre><code># mkfifo inp out
  # bc -ql  &lt;inp  &gt;out  &amp;
  [1] 6766
  #
  # exec 3&gt;inp  4&lt;out
  # echo "scale=3; 4/5;" &gt;&amp;3
  # read a &lt;&amp;4; echo $a
  .800
  #
  # awk ' BEGIN { printf("4/5\n") &gt;"/dev/fd/3"; exit 1;} '
  # read a &lt;&amp;4; echo $a
  .800
  #
  # awk ' BEGIN { printf("4/5\n") &gt;"/dev/fd/3"; exit 1;} '
  # awk ' BEGIN { getline a &lt;"/dev/fd/4"; printf("%s\n", a); } '
  ^C
  </code></pre>
  
  <p>In BASH environment I can communicate with bc program using fifo.
  But in awk I can write but no read with getline function.
  How can I read from "/dev/fd/4" in awk.</p>
  
  <p><strong>My awk version is: mawk 1.3.3</strong> Nov 1996, Copyright (C) Michael D. Brennan</p>
  
  <p>Thanks
  Laci</p>
  
  <p>Continued:</p>
  
  <p>I did some further experiment and I summarize my result.
  Awk script language suits best for my task,
  and I need to use "bc" because I have to count with very long numbers (about 100 digits).
  The next two scripts show that using named pipe is faster than unnamed (about 83 times).</p>
  
  <p>1) With unnamed pipe:</p>
  
  <pre><code># time for((i=6000;i;i--)); do a=`echo "$i/1"|bc -ql`; done
  real    0m13.936s
  </code></pre>
  
  <p>2) With named pipe:</p>
  
  <pre><code># mkfifo in out
  # bc -ql &lt;in &gt;out &amp;
  # exec 3&gt;in 4&lt;out
  #
  # time for((i=500000;i;i--)); do echo "$i/1" &gt;&amp;3; read a &lt;&amp;4; done
  real    0m14.391s
  </code></pre>
  
  <p>3) In the awk environment  the bc usage is a bit slower (about 18 times) than in bash but it works this way:</p>
  
  <pre><code># time awk ' BEGIN {
  #               for(i=30000;i;i--){
  #                   printf("%d/1\n",i) &gt;"/dev/fd/3";
  #                   system("read a &lt;/dev/fd/4; echo $a &gt;tmp_1");
  #                   getline a &lt;"tmp_1"; close("tmp_1");}
  #                  } '
  real    0m14.178s
  </code></pre>
  
  <p>4)What can be the problem when I try to do accordig to "man awk" ? :</p>
  
  <pre><code># awk ' BEGIN {
  #         for(i=4;i;i--){
  #         printf("%d/1\n",i) &gt;"/dev/fd/3"; system("sleep .1");
  #        "read a &lt;/dev/fd/4; echo $a" | getline a ;print a;}
  #      } '
  4.000
  4.000
  4.000
  4.000
  </code></pre>
  
  <p>The above "awk" script was able to pick up only the first number from the pipe.
  The  other three numbers remained in the pipe.
  These will be visible when I'm reading the pipe after the above awk script.</p>
  
  <pre><code># for((;;)); do read a &lt;/dev/fd/4; echo $a; done
  3.000
  2.000
  1.000
  </code></pre>
  
  <p>Thanks for gawk.</p>