Friday, May 18, 2012

[Bash] convert agu citation to bibtex format

#!/bin/bash
# convert citation string from agu website to a bibtex format
# usage:
#           agu2bib.sh 'citeString'
#   note: 
#          1: need single quotations
#          2: the whole command should be in one line
#         www.scriptdemo.blogspot.ca
getLastChar()
{
  echo -n $* | tail -c1
}

fixVolNum()
{
  # get number from volume-string
  volstr=$1
  if [ `getLastChar ${volstr}` == ")" ]; then
     numStr=`echo ${volstr} | awk -F\( '{print $2}' | rev | cut -c2- | rev`
     volstr=`echo ${numStr} | sed -e "s/\(${numStr}\)//"`
     echo "${volstr} ${numStr}" && exit
  else
     nf=`echo $volstr | awk -F\: '{print NF}'`
     if [ ${nf} -eq 2 ]; then
        echo ${volstr} | awk -F\: '{print $1" "$2}' && exit
     else
        echo "${volstr}" && exit
     fi
  fi
}
fixPageNum()
{
   echo $1 | sed -e 's/–/--/g' | sed -e 's/----/--/'
}

revName()
{
   nf=`echo $* | awk '{print NF}'`
   if [ $nf -ge 2 ]; then
      lastName=`echo $* | rev | awk '{print $1}' | rev`
      restName=`echo $* | sed -e "s/${lastName}//" | sed -e 's/\.\ /\./g' | sed -e 's/\ $//'`
      echo "${lastName}, ${restName}"
   else
      echo $*
   fi
}
getAuthor()
{
    nf=`echo $* | awk --field-separator=" and " '{print NF}'`
    if [ ${nf} -eq 1 ]; then
       # one author
       # Myers, P. G. ==> Myers, P.G.
       echo $* | sed -e 's/\.\ /\./g'
       exit
    else
       # more than one author
       lastOne=`echo $* | awk --field-separator=" and " '{print $2}'`
       lastOne=`revName ${lastOne}`
       # how to get first one
       str0=`echo $* | awk --field-separator=" and " '{print $1}' | sed -e 's/\,$//'`
       nf=`echo ${str0} | awk -F\, '{print NF}'`
       if [ ${nf} -eq 1 ]; then
          echo "${str0} and ${lastOne}"
          exit
       fi
       fl2=`echo ${str0} | awk -F\, '{print $2}'`
       indNext=2
       if [ `getLastChar ${fl2}` == "." ]; then
          # take first two fields as the first author
          fl1=`echo ${str0} | awk -F\, '{print $1}'`
          fl2=`echo ${fl2} | sed -e 's/\.\ /\./g' | sed -e 's/\ $//'`
          firstOne="${fl1}, ${fl2}"
          indNext=3
       fi
       outStr=${firstOne}
       for (( n=${indNext}; n<=${nf}; n++))
       do
           cfl=`echo ${str0} | cut -d\, -f ${n}`
           cnameStr=`revName ${cfl}`
           outStr="${outStr} and ${cnameStr}"
       done
       echo "${outStr} and ${lastOne}" && exit
    fi
}

[ $# -eq 0 ] && sed -n '2,7p' `which agu2bib.sh` && exit
isDebug=0
nLen=4
inStr=$*
nTLen=${#inStr}
nLoop=`expr ${nTLen} - ${nLen} - 1`
isFound=0
jTag=""

for (( nL=1; nL<=${nLoop}; nL++ ))
do
    subStr=${inStr:${nL}:${nLen}} # index starts from ZERO
    if [[ ${subStr} =~ "[1-2][0-9][0-9][0-9]" ]]; then
       [ ${isDebug} -eq 1 ] && set -x
       nL0=${nL}
       tmpChar=`echo ${inStr} | cut -c${nL0}`
       while [ "${tmpChar}" != ' ' ]
       do
             nL0=`expr ${nL0} - 1`
             tmpChar=`echo ${inStr} | cut -c${nL0}`
       done
       myStr0=`echo ${inStr} | cut -c-${nL0} | sed -e 's/\ $//g' -e 's/\,$//g'`

       nL1=`expr ${nL} + ${nLen} + 1`
       tmpChar=`echo ${inStr} | cut -c${nL1}`
       [ "${tmpChar}" == ":" ] && jTag="ams"
       while [ "${tmpChar}" != ' ' ]
       do
             [ "${tmpChar}" == ":" ] && jTag="ams"
             nL1=`expr ${nL1} + 1`
             tmpChar=`echo ${inStr} | cut -c${nL1}`
       done
       myStr1=`echo ${inStr} | cut -c${nL1}-`
       yearStr=${subStr}
       isFound=1
       break
    fi
done
[ ${isDebug} -eq 1 ] && set +x

[ ${isFound} -eq 0 ] && echo "can find the publicsh time!" && exit
[ ${isDebug} -eq 1 ] && echo "second half: ${myStr1}"

# get doi
doi=`echo ${myStr1} | rev | awk -F, '{print $1}' | rev | sed -e 's/\ //g'`
if [[ ${doi} =~ "doi*" ]] || [[ ${doi} =~ "DOI*" ]]; then
   isDOI=1
   doi=`echo ${doi} | sed -e 's/\.$//'`
   pages=`echo ${myStr1} | rev | awk -F, '{print $2}' | rev | sed -e 's/\ //g'`
   vol=`echo ${myStr1} | rev | awk -F, '{print $3}' | rev | sed -e 's/\ //g'`
   if [ "${#jTag}" -eq 0 ]; then
      jour=`echo ${myStr1} | rev | awk -F, '{print $4}' | rev`
   fi
else
   isDOI=0
   pages=${doi} && unset doi
   pages=`echo ${pages} | sed -e 's/\.$//'`
   vol=`echo ${myStr1} | rev | awk -F, '{print $2}' | rev | sed -e 's/\ //g'`
   if [ "${#jTag}" -eq 0 ]; then
      jour=`echo ${myStr1} | rev | awk -F, '{print $3}' | rev`
   fi
fi
if [ ${#jTag} -eq 0 ]; then
   indOfJour=`awk -v a="${myStr1}" -v b="${jour}" 'BEGIN{print index(a,b)}'`
   indOfJour=`expr ${indOfJour} - 3`
   title=`echo ${myStr1} | cut -c-${indOfJour}`
else
   title=`echo ${myStr1} | awk -F\. '{print $1}'`
   nL1=`expr ${#title} + 2`
   myStr1=`echo ${myStr1} | cut -c${nL1}-`
   jour=`echo ${myStr1} | awk -F\, '{print $1}'`
   nf=`echo ${myStr0} | awk -F\, '{print NF}'`
   if [ ${nf} -gt 2 ]; then
      myStr0=`echo ${myStr0} | rev | sed -e 's/\,/\ dna\ /' | rev`
   fi
fi

# get author string
[ ${isDebug} -eq 1 ] && echo "first half: ${myStr0}"
author=`getAuthor "${myStr0}"`
pages=`fixPageNum ${pages}`
volStr=`fixVolNum ${vol}`
vol=`echo ${volStr} | awk '{print $1}'`
num=`echo ${volStr} | awk '{print $2}'`

#generate the key
mykey=`echo ${author} | awk -F\, '{print $1}'`
mykey="${mykey}${yearStr}"
titleKey=`echo ${title} | awk '{print $1""$2}'`
mykey=`echo "${mykey}${titleKey}" | awk '{print tolower($0)}' | sed -e 's/\-//g'`

#output
echo "@article{${mykey},"
echo " author={${author}},"
echo " title = {{${title}}},"
echo " journal = {${jour}},"
echo " year = {${yearStr}},"
echo " volume = {${vol}},"
[ ${#num} -ne 0 ] && echo " number = { ${num}},"
if [ ${isDOI} -eq 1 ]; then
   echo " pages = {${pages}},"
   echo " doi = {${doi}}"
else
   echo " pages = {${pages}}"
fi
echo "}"

Example:

Output:

Monday, May 7, 2012

[Bash] combine eps files into a single one

#!/bin/bash
#  to combine several eps files into a single eps file
# Usage:
#        combineEPS.sh eps-file[s] -o eps-combined.eps -nC nCol -nR nRow
# e.g.,
#        Given fig04a.eps, fig04b.eps, fig04c.eps, fig04d.eps,
#        to create a single 2x2 eps file, fig4.eps, just run:
#        combineEPS.sh fig04?.eps -o fig4.eps -nC 2 -nR 2
#        
# dependencies:
#        latex, dvips, ps2pdf, pdftops, pdfcrop
#        pdfcrop is from http://pdfcrop.sourceforge.net
#        http://scriptdemo.blogspot.ca

chkcmd()
{
  for nf in $*
  do
     isAvailable=`which ${nf} 2< /dev/null`
     [ ${#isAvailable} -eq 0 ] && echo 0 && exit
  done
  echo 1
}

# check the dependencies
isCMDOkay=`chkcmd latex dvips ps2pdf pdfcrop pdftops`
if [ ${isCMDOkay} -eq 0 ]; then
   isCMDOay=`which latex`
   isCMDOay=`which dvips`
   isCMDOay=`which ps2pdf`
   isCMDOay=`which pdfcrop`
   isCMDOay=`which pdftops`
   exit
fi

nfile=0
isEPSFname=0
isnCol=0
isnRow=0
isDel=0
isCaption=0

[ $# -eq 0 ] && sed -n '2,9p' `which combineEPS.sh` && exit

while test -n "$1"
do
  case "$1" in
    -nC|-nc|-nCol|-ncol|-Ncol)
       nCol=$2
       isnCol=1
       shift
       shift
       ;;
    -nR|-nr|-nRow|-Nrow|-nrow)
       nRow=$2
       isnRow=1
       shift
       shift
       ;;
    -title|-Title|-Caption|-caption)
       myCaption=$2
       isCaption=1
       shift
       shift
       ;;
    -d|-delete|-del|-D)
       isDel=1;
       shift
       ;;
    -o|-O)
       epsfname=$2
       isEPSFname=1
       shift
       shift
       ;;
     *)
       sufstr=`echo $1 | awk -F. '{print $2}'`
       if [ ${#sufstr} -eq 0 ]; then
          tmpfile="$1".eps
          [ -f ${tmpfile} ] && epsfile[$nfile]=${tmpfile}.eps
       elif [ $sufstr == "eps" ]; then
          [ -f $1 ] && epsfile[$nfile]=$1
       fi
       nfile=`expr $nfile + 1`
       shift
       ;;
  esac
done

[ ${isEPSFname} -eq 0 ] && epsfname="eps-combined.eps"
if [ ${isnCol} -eq 1 ] && [ ${isnRow} -eq 0 ]; then
   nRow=`echo "${nfile}/${nCol}" | bc -l | awk '{ if ($1 == int($1)) {printf "%d\n", $1} else { if ($1>0) {printf "%d\n",int($1)+1 } else {printf "%d\n",int($1)} } }'`
fi
if [ ${isnRow} -eq 1 ] && [ ${isnCol} -eq 0 ]; then
   nCol=`echo "${nfile}/${nRow}" | bc -l | awk '{ if ($1 == int($1)) {printf "%d\n", $1} else { if ($1>0) {print "%d\n",int($1)+1 } else {printf "%d\n",int($1)} } }'`
fi
if [ $isnRow -eq 0 ] && [ $isnCol -eq 0 ]; then
   nCol=1
   nRow=${nfile}
fi

colstr=`printf "%*s\n" ${nCol} " " | sed -e 's/\ /c/g'`
nwidth=$(printf "%.2f\n" `echo "1/${nCol}" | bc -l`)
[ ${nwidth} == "1.00" ] && nwidth=""
#echo -e "nCol=${nCol}\nnRow=${nRow}\nnWid=${nwidth}"

# header of tex file
texfile=${epsfname%.*}.tex
dvifile=${epsfname%.*}.dvi
psfile=${epsfname%.*}.ps
logfile=${epsfname%.*}.log
auxfile=${epsfname%.*}.aux
pdfname=${epsfname%.*}.pdf

header[0]='\documentclass[letterpaper,12pt]{article}'
header[1]='\usepackage{epsfig}'
header[2]='\begin{document}'
header[3]='\thispagestyle{empty}'
header[4]='\begin{figure}'
header[5]='\centering'
header[6]="\begin{tabular}{${colstr}}"
printf "%s\n" ${header[*]} > ${texfile}
n=0
nfileC=`expr ${nfile} - 1`
for nL in `seq 1 ${nRow}`
do
    for nC in `seq 1 ${nCol}`
    do
       if [ $n -lt ${nfile} ]; then
          epsname=${epsfile[$n]}
          if [ ${nC} -eq ${nCol} ]; then
             if [ ${nL} -eq ${nRow} ]; then
                tmpstr=""
             else
                tmpstr=" \\\\"
             fi
          else
             tmpstr=" &"
          fi

          [ ${n} -eq ${nfileC} ] && tmpstr=""
          figline[$n]="\epsfig{file=${epsname},width=${nwidth}\linewidth,clip=}${tmpstr}"
          #printf "%s\n" "${figline[$n]}" >> ${texfile}
          n=`expr $n + 1`
       fi
    done
done
printf "%s %s\n" ${figline[*]} >> ${texfile}

# tail of tex file
mytail[0]="\end{tabular}"
if [ ${isCaption} -eq 1 ]; then
   mytail[1]="\caption${myCaption}"
else
   mytail[1]=""
fi
mytail[2]="\end{figure}"
mytail[3]="\end{document}"
printf "%s\n" ${mytail[*]} >> ${texfile}

#compile the tex file
latex ${texfile}
dvips -t letter -Ppdf -o ${psfile} ${dvifile} && rm -f ${dvifile}
ps2pdf ${psfile} && rm -f ${psfile} ${auxfile} ${logfile}
[ ${isDel} -eq 1 ] && rm -f ${texfile}

# crop the pdf file
pdfname=${epsfname%.*}.pdf
pdfcrop ${pdfname} && mv ${pdfname%.*}-crop.pdf ${pdfname} && pdftops -eps ${pdfname} ${epsfname}

[Bash] Check the existence of a command

#!/bin/bash
# check the existence of a command [ base on the returns of which and alias ]
# usage:
#           chkcmd.sh command-list
# e.g.,
#           chkcmd.sh pdfit
#           http://scriptdemo.blogspot.ca

source ~/.bashrc
if [ $# -eq 0 ]; then
   sed -n '2,6p' `which chkcmd.sh`
   exit
else
   for mycmd in $*
   do
      isInPath=`which ${mycmd} 2< /dev/null`
      if [ ${#isInPath} -eq 0 ]; then
         isAlias=`alias ${mycmd} 2< /dev/null`
         if [ ${#isAlias} -eq 0 ]; then
            echo "${mycmd} is not in the path";
         else
            echo "${mycmd} is an aliased command";
         fi
      else
         echo "${mycmd} is in the path";
      fi
   done
fi

ShowCalendar