Posts

Cost Of A SubShell

bash-3.2$ time (for x in {1..210000}; do : ; done) real    0m0.934s user    0m0.911s sys    0m0.020s bash-3.2$ time for x in {1..1000}; do (:) ; done real    0m0.967s user    0m0.309s sys    0m0.632s # The sys cost of forking 1000 times in 0.632 seconds just under a millisecond per subshell. # to create the subshell. This is a lot more than I would have expected for a naked fork so  # lots of other stuff is probably going on.

Subprocess without job control spew

# If you don't want to have [3] and [3]+ Done and all that stuff: ( (do_some_work_here; do_some_more)& ) # or ( just_do_some_work arg arg arg & ) # E.g. from bithon. # Write to a fd (which is a named pipe) all of the arguments # to the function then write a special end of stream statement. # Do all this in the background (to avoid pipe deadlock) and  # launch from a subshell to avoid job control spew. Remember # fork on Linux (or Mac OS) is < 1000 cycles... i.e. less than # one millionth of a second, so don't worry too much about this # approach from a performance point of view (though subshells  # are actually quite a bit more expensive). ( (echo "$@" >&3; echo 'print "\nbithon-eos"' >&3)& ) # Putting the background process in a subshell removes the job control spew.

Function which will accept stdin or arguments

function launch_python {   exec 3>&-   exec 4<&-   pyin=$(mktemp -u)   pyot=$(mktemp -u)   mkfifo $pyin   mkfifo $pyot   python -u -i <$pyin &>$pyot &   pypid=$!   exec 3> $pyin   exec 4< $pyot   rm $pyin   rm $pyot   echo print >&3   while read -u 4 line && [ "${line}" != '>>>' ]   do     echo  "# ${line}"   done   echo 'import sys;sys.ps2=""' >&3 } function py_read {   local line   while read -u 4 line && [ "${line}" != 'bithon-eos' ]   do     while [ "${line#>>> }" != "${line}" ]     do         line=${line#>>> }     done     [ ${line} == '>>>' ] && continue     echo "${line}"   done } function _ppy {   local line   IFS=''   while r...

Bithon Update 1

# Probably one of many, this is more bash style in the logic statements and better handling of eos. function launch_python {   exec 3>&-   exec 4<&-   pyin=$(mktemp -u)   pyot=$(mktemp -u)   mkfifo $pyin   mkfifo $pyot   python -u -i <$pyin &>$pyot &   pypid=$!   exec 3> $pyin   exec 4< $pyot   rm $pyin   rm $pyot   echo print >&3   while read -u 4 line && [ "${line}" != '>>>' ]   do     echo  "# ${line}"   done   echo 'import sys;sys.ps2=""' >&3 } function py_read {   local line   while read -u 4 line && [ "${line}" != 'bithon-eos' ]   do     [ "${line}" == '>>>' ] && continue     line="${line#>>> }"     [ "${line}" == '>>>' ] && continue     echo "${line#>>>}"   done } function...

Bithon: Run Python Interactively Inside Bash

cat > bithon.sh << EOF # This script allows python to run as child of bash # attached to anonymous pipes and all commands in # bash starting py are sent to python.   function launch_python {   # Close any existing use of these fds.   exec 3>&-   exec 4<&-   pyin=$(mktemp -u)   pyot=$(mktemp -u)   mkfifo $pyin   mkfifo $pyot   python -u -i <$pyin &>$pyot &   pypid=$!   exec 3> $pyin   exec 4< $pyot   # Make the pipes 'anonymous'.   rm $pyin   rm $pyot   echo print >&3   while read -u 4 line   do     if [ "${line}" == '>>>' ]     then       break     fi     echo  "# ${line}"   done   echo 'import sys;sys.ps2=""' >&3 } function py_read {   local line   while read -u 4 line   do     if [ "${line}" == '...

Local scope variables

# local makes variables local. function thing { local l=8;echo $l;} l=3 echo $l 3 thing 8 echo $l 3 ... # declare does exactly the same thing. function thing { declare l=8;echo $l ;} l=3 echo $l 3 thing 8 echo $l 3 ... # otherwise variables are global even inside functions. function thing { l=8;echo $l ;} l=3 echo $l 3 thing 8 echo $l 8

Pretty Print Percentiles Of Decimal Numeric List

function sort_numeric_array {     sort <(echo $@ | tr ' ' "\n") --numeric-sort | tr "\n" ' ' } dataA=($(rand 101 1000)) dataB=($(rand 101 1000000)) for idx in {0..100} do     data[$idx]="${dataA[idx]}.${dataB[idx]}" done data=($(sort_numeric_array ${data[@]})) len=${#data[@]} data[$len]=0 function pctiles {     echo scale=6     for idx in {0..10}     do         if [ $idx == 0 ]         then             place=0         else             place=$((((len-1)*idx*10)/10))         fi         second=$((place%10))         first=$((10-second))         place=$((place/10))         plus1=$((place+1))         if [ $plus1 -lt $len ]         then     ...