home *** CD-ROM | disk | FTP | other *** search
/ Skunkware 5 / Skunkware 5.iso / src / Tools / MotifApp / ch10 / CountWordsCmd.C next >
Encoding:
C/C++ Source or Header  |  1995-05-03  |  4.4 KB  |  192 lines

  1. ///////////////////////////////////////////////////////////////////////////////
  2. //////////////////////////////////////////////////////////////////////////////
  3. //         This example code is from the book:
  4. //
  5. //           Object-Oriented Programming with C++ and OSF/Motif
  6. //         by
  7. //           Douglas Young
  8. //           Prentice Hall, 1992
  9. //           ISBN 0-13-630252-1    
  10. //
  11. //         Copyright 1991 by Prentice Hall
  12. //         All Rights Reserved
  13. //
  14. //  Permission to use, copy, modify, and distribute this software for 
  15. //  any purpose except publication and without fee is hereby granted, provided 
  16. //  that the above copyright notice appear in all copies of the software.
  17. ///////////////////////////////////////////////////////////////////////////////
  18. //////////////////////////////////////////////////////////////////////////////
  19.  
  20.  
  21. ////////////////////////////////////////////////////////////////
  22. // CountWordsCmd.C: A simple test of the InterruptibleCmd class
  23. ///////////////////////////////////////////////////////////////
  24. #include <stdio.h>
  25. #include <sys/stat.h>
  26. #include <sys/types.h>
  27. #include "CountWordsCmd.h"
  28. #include "InfoDialogManager.h"
  29.  
  30. CountWordsCmd::CountWordsCmd ( char *name, 
  31.                   int   active, 
  32.                   char *filename ) : 
  33.                   InterruptibleCmd ( name, active )
  34. {
  35.     struct stat statInfo;
  36.     
  37.     // Initialize data members
  38.     
  39.     _bytesRead = 0;       
  40.     _fileSize  = 0;       
  41.     _numWords  = 0;        
  42.     _list      = NULL; 
  43.     _percentDone = 0;
  44.     
  45.     // Open the given file and post a warning in case of failure
  46.     
  47.     if( ( _fd = fopen ( filename, "r" ) ) == NULL ) 
  48.     {
  49.     char buf[BUFSIZ];
  50.     
  51.     sprintf ( buf, "Can't open %s", filename );
  52.     
  53.     theInfoDialogManager->post ( buf );
  54.     }
  55.     else
  56.     {
  57.     // Check the size of the file, to use as a basis for
  58.     // reporting progress. Don't bother counting if the file
  59.     // is empty.
  60.     
  61.     char buf[BUFSIZ];
  62.     
  63.     if ( stat ( filename, &statInfo ) == 0 )
  64.         _fileSize = statInfo.st_size;
  65.     
  66.     if ( _fileSize == 0 )
  67.     {
  68.         sprintf ( buf, "%s is empty!", filename );
  69.         
  70.         theInfoDialogManager->post ( buf );
  71.         
  72.         fclose ( _fd );
  73.         _fd = 0;
  74.     }
  75.     }
  76. }
  77.  
  78. CountWordsCmd::~CountWordsCmd ()
  79. {
  80.     // Only close the file if it was succesfully opened
  81.     
  82.     if ( _fd )
  83.     fclose ( _fd );
  84.     
  85.     for ( int i=0; i < _numWords; i++ )    
  86.     delete _list[i];
  87.     
  88.     delete _list;
  89. }
  90.  
  91. void CountWordsCmd::doit()
  92. {
  93.     char  buf[BUFSIZ];
  94.     char *sep = " !@#$%^&*()_+=-}{][|\';:\"?></.,`~\\\n\t";
  95.     int   percent;
  96.     
  97.     // If the file has not been opened, indicate that the task 
  98.     // is finished.
  99.     
  100.     if ( !_fd )
  101.     {
  102.     _done = TRUE;
  103.     return;
  104.     }
  105.     
  106.     // Read a few lines each time doit() is called
  107.     
  108.     for ( int i = 0; i < 20; i++ )
  109.     {
  110.     char *result;
  111.     char *word;
  112.     
  113.     // Read in one line of text, indicating that the
  114.     // task is done if we reach end-of-file
  115.     
  116.     if ( ( result = fgets ( buf, BUFSIZ, _fd ) ) == NULL )
  117.     {
  118.         _done = TRUE;
  119.         return;
  120.     }
  121.     
  122.     // Compute the total characters read for progress report
  123.     
  124.     _bytesRead += strlen ( buf );
  125.     
  126.     // Extract the first full word and save it in the word list
  127.     
  128.     word = strtok ( buf, sep );
  129.     
  130.     saveWord ( word );
  131.     
  132.     // Continue to extract words until the line is exhausted
  133.     
  134.     while ( ( word = strtok ( NULL, sep ) ) != NULL )
  135.         saveWord ( word );
  136.     }
  137.     
  138.     // Update the busy dialog and report progress as 
  139.     // the percentage of the file read so far. Only report if the
  140.     // percent done has changed.
  141.     
  142.     percent =  (int) ((float) _bytesRead / (float) _fileSize * 100);
  143.     
  144.     if ( _percentDone != percent )
  145.     {
  146.     
  147.     _percentDone = percent;
  148.     
  149.     sprintf ( buf, "Counting, Please Wait...\n %d %% Completed",
  150.          _percentDone );
  151.     
  152.     updateMessage( buf );
  153.     
  154.     }
  155. }
  156.  
  157. void CountWordsCmd::saveWord ( char * word )
  158. {
  159.     // Check for valid input
  160.     
  161.     if ( !word )
  162.     return;
  163.     
  164.     // Search for the word. Increment the count if found
  165.     
  166.     for ( int i = 0; i < _numWords; i++ )    
  167.     {
  168.     if ( *_list[i] == word ) // Note use of overloaded operator==
  169.     {
  170.         ( *_list[i] )++;
  171.         return;
  172.     }
  173.     }
  174.     
  175.     // If not found, create a new Word object and add it to the
  176.     // list, increasing the size of the list for each new word.
  177.     
  178.     Word *obj = new Word ( word );
  179.     
  180.     Word **newList = new Word*[_numWords + 1];
  181.     
  182.     for ( i = 0; i < _numWords; i++ )
  183.     newList[i] = _list[i];
  184.     
  185.     newList[_numWords] = obj;
  186.     delete _list;
  187.     _list = newList;
  188.     
  189.     _numWords++;
  190. }
  191.  
  192.