home *** CD-ROM | disk | FTP | other *** search
/ CP/M / CPM_CDROM.iso / lambda / soundpot / p / ut-c.lbr / PREP.CZ / PREP.C
Encoding:
C/C++ Source or Header  |  1993-10-25  |  5.4 KB  |  206 lines

  1. /*  prep.c -- UTOOL. Convert a text file (including ws doc files)
  2.      to one word per line.
  3.      author: David H. Wolen
  4.      last change: 3/9/83
  5.  
  6.      usage:   prep <letter.doc -i dict.dat
  7.      options: -o list.dat   only do words on file
  8.               -i list.dat   ignore words on file
  9.               -d            preface output words with input sequence numbers
  10.  
  11.      input:    STDIN
  12.      output:   STDOUT
  13.  
  14.      notes:  (a) files for -o and -i must be prepared by prep
  15.                  and sort (-f and -u)
  16.              (b) can't use both -o and -i
  17.              (c) output is lower case
  18.              (d) max file size for -o or -i is 1000 lines or
  19.                  about 30K.
  20.  
  21.      linkage: a:clink prep -f dio -ca (uses deff3.crl)
  22. */
  23.  
  24. #include "a:bdscio.h"
  25. #include "dio.h"
  26. #define  STDOUT 1
  27. #define  STDERR 4
  28. #define  LINES  1000          /* size of list for -o and -i */
  29.  
  30. char *listp[LINES];           /* pointers to list items */
  31. int  nlist;                   /* number of list items */
  32.  
  33. main(argc,argv)
  34. int  argc;
  35. char *argv[];
  36. {
  37.      int  only, ignore, sequence, wcount;
  38.      char *s, word[MAXLINE];
  39.  
  40.      dioinit(&argc,argv);
  41.      only=ignore=sequence=FALSE;
  42.      wcount=0;
  43.  
  44.      while(--argc > 0 && (*++argv)[0]=='-')
  45.           for(s=argv[0]+1; *s != '\0'; s++)
  46.                switch(*s)
  47.                     {case 'O':
  48.                          only=TRUE;
  49.                          break;
  50.                     case 'I':
  51.                          ignore=TRUE;
  52.                          break;
  53.                     case 'D':
  54.                          sequence=TRUE;
  55.                          break;
  56.                     default:
  57.                          error("prep: invalid option");
  58.                     }
  59.  
  60.      if(only && ignore)
  61.           error("prep: can't use both -o and -i");
  62.  
  63.      if(only || ignore)
  64.           readlist(*argv);
  65.  
  66.      while(getword(word))
  67.           {wcount++;
  68.           if(ignore)
  69.                {if(!pmatch(word) && sequence)
  70.                     fprintf(STDOUT,"%d: %s\n",wcount,word);
  71.                if(!pmatch(word) && !sequence)
  72.                     fprintf(STDOUT,"%s\n",word);
  73.                }
  74.           else if(only)
  75.                {if(pmatch(word) && sequence)
  76.                     fprintf(STDOUT,"%d: %s\n",wcount,word);
  77.                if(pmatch(word) && !sequence)
  78.                     fprintf(STDOUT,"%s\n",word);
  79.                }
  80.           else
  81.                {if(sequence)
  82.                     fprintf(STDOUT,"%d: %s\n",wcount,word);
  83.                else
  84.                     fprintf(STDOUT,"%s\n",word);
  85.                }
  86.           }
  87.  
  88.      dioflush();
  89. }
  90.  
  91.  
  92.  
  93. /*  readlist -- read and store exclusion or inclusion
  94.           list.  Check to be sure list is sorted and unique.
  95. */
  96. readlist(filename)
  97. char *filename;
  98. {
  99.      int  len, i;
  100.      char ibuf[BUFSIZ], line[MAXLINE], *sbrk(), *p;
  101.  
  102.      if(fopen(filename,ibuf)==ERROR)
  103.           error("prep: can't open list file");
  104.  
  105.      nlist=0;
  106.  
  107.      while(fgets(line,ibuf))
  108.           {if(nlist > LINES)  error("prep: too many lines in list file");
  109.           line[strlen(line)-1]='\0';   /* zap '\n' */
  110.           len=strlen(line) +1;
  111.           if((p=sbrk(len))==ERROR)  error("prep: too many chars on list file");
  112.           strcpy(p,line);
  113.           listp[nlist++]=p;
  114.           }
  115.  
  116.      if(nlist < 1)  error("prep: empty list file");
  117.  
  118.      for(i=1; i<nlist; i++)
  119.           if(pstrcmp(listp[i-1],listp[i]) >=0)
  120.                error("prep: list isn't sorted or has duplicates");
  121. }
  122.  
  123.  
  124.  
  125. /* pstrcmp -- compare strings.  Return <0 if s<t; 0 if
  126.           s==t; >0 if s>t.  For equality, strings must be
  127.           equal in length.  Fold lower into upper case
  128.           before comparison.
  129. */
  130. pstrcmp(s,t)
  131. char *s, *t;
  132. {
  133.      for(; *s != '\0'; s++, t++)
  134.           if(toupper(*s) != toupper(*t))
  135.                return(toupper(*s)-toupper(*t));
  136.  
  137.      if(*t == '\0')  return(0);
  138.      else
  139.           return(-1);
  140. }
  141.  
  142.  
  143.  
  144. /*  getword -- get the next word from the standard input.
  145.           Return TRUE for got a word, FALSE for EOF.
  146. */
  147. getword(word)
  148. char *word;
  149. {
  150.      int  i, c;
  151.  
  152.      i=0;
  153.  
  154.      while(1)  /* find start of word */
  155.           {if((c=getchar())==EOF)  return(FALSE);
  156.           c &= 0177;          /* Wordstar hi bit */
  157.           if(isalpha(c))  break;
  158.           }
  159.  
  160.      word[i++]=tolower(c);
  161.  
  162.      while(1)
  163.           {if((c=getchar())==EOF) /* push back EOF for next call */
  164.                {ungetch(c);
  165.                break;
  166.                }
  167.           c &= 0177;
  168.           if(!isalpha(c) && c!='\'')  break;      /* allow ' within a word */
  169.           else
  170.                word[i++]=tolower(c);
  171.           }
  172.  
  173.      if(word[i-1]=='\'')
  174.           word[i-1]='\0';
  175.      else
  176.           word[i]='\0';
  177.  
  178.      return(TRUE);
  179. }
  180.  
  181.  
  182.  
  183. /*  pmatch -- return TRUE if word is in list, else FALSE.
  184.           Ignore case in the comparison.
  185. */
  186. pmatch(word)
  187. char *word;
  188. {
  189.      int  low, mid, high;
  190.  
  191.      low=0;
  192.      high=nlist-1;
  193.  
  194.      while(low <= high)  /* binary search */
  195.           {mid=(low+high)/2;
  196.           if(pstrcmp(word,listp[mid]) < 0)
  197.                high=mid-1;
  198.           else if (pstrcmp(word,listp[mid]) >0)
  199.                low=mid+1;
  200.           else           /* found match */
  201.                return(TRUE);
  202.           }
  203.  
  204.      return(FALSE);
  205. }
  206.