/*
             CREATOR: DAn williams
                DATE:
         DESCRIPTION:
            FILENAME:    .c
             STARTED:
    OPERATING SYSTEM: Linux
1st VERSION FINISHED:



*/


#include <stdio.h>
#include <string.h>
//#include <conio.h>  // for dos
#include <stdlib.h>
#include "wordlist.c"

//global variables

#define TRUE  1
#define FALSE 0

#define capchar(c) ((c >= 'a') && (c <= 'z')) ? c-0x20 : c
#define lowchar(c) ((c >= 'A') && (c <= 'Z')) ? c+0x20 : c



#define KNOWNWORD(s) (strstr( wordlist.data, s ) != NULL)

//--
#define ADVERB(s)       (strstr( adverbs.data,   s ) != NULL)
#define DETERMINER(s)   (strstr( determiners.data,   s ) != NULL)
#define PREDICATE(s)    (strstr( predicates.data,    s ) != NULL)
#define PRONOUN(s)      (strstr( pronouns.data,      s ) != NULL)
#define ADJECTIVE(s)    (strstr( adjectives.data,    s ) != NULL)
#define PROPERNOUN(s)   (strstr( propernouns.data,   s ) != NULL)
#define VERB(s)         (strstr( verbs.data,         s ) != NULL)
#define NOUN(s)         (strstr( nouns.data,         s ) != NULL)
#define CONJUNCTION(s)  (strstr( conjunctions.data,  s ) != NULL)
#define INTERJECTION(s) (strstr( interjections.data, s ) != NULL)	
#define PREPOSITION(s)  (strstr( prepositions.data,  s ) != NULL)

//--


void analize_utterance(char *info);

//wordlist_t  wordlist;
wordlist_t  adverbs;
wordlist_t  determiners;
wordlist_t  predicates;
wordlist_t  pronouns;
wordlist_t  adjectives;
wordlist_t  propernouns;
wordlist_t  verbs;
wordlist_t  nouns;
wordlist_t  conjunctions;
wordlist_t  interjections;
wordlist_t  prepositions;



int main(int argc, char** argv)
{
  // local variables
  
  FILE *input;
  char temp[1024];
  int retcode;
  
  retcode = 0;
  
  printf(" This program analizes text\n");
  printf(" Written by Dan Williams DEC 25 2004 \n");
  
  
  if (argc < 2) {                          // do we have input paramiters??   
      puts("Need input paramiters\n");
      return 0;    
  }
  
  if ((input = fopen(argv[1], "rt")) == NULL) {  //open text file 'param 1' w/ err chk 
      printf("Unable to open %s for input.\n", argv[1]);
      return -1;
  }
  
  //--
  InitWordList( &adverbs );
  InitWordList( &determiners );
  InitWordList( &predicates );
  InitWordList( &pronouns );
  InitWordList( &adjectives );
  InitWordList( &propernouns );
  InitWordList( &verbs );
  InitWordList( &nouns );
  InitWordList( &conjunctions );
  InitWordList( &interjections );
  InitWordList( &prepositions );
  
  // preload some words
  AddWord( &adverbs, " how when where ");
  AddWord( &determiners, "" );
  AddWord( &predicates, "" );
  AddWord( &pronouns, " i she he it her his they who that ");
  AddWord( &adjectives, " the my an a what which ");
  AddWord( &propernouns, "" );
  AddWord( &verbs, " am are is was were been can have does will did ");
  AddWord( &nouns, "" );
  AddWord( &conjunctions, " and but or ");
  AddWord( &interjections, " hi hello howdy hiya bye goodbye hey ");
  AddWord( &prepositions, " in to ");
      
  while( fgets(temp, 1022, input) != NULL) {
     analize_utterance(temp);       
//     fgets(temp, 1000, stdin);  // pause for keyboard input
  }  
  
  printf("Resulting verbs : %s \n", verbs.data);
  printf("Resulting pronouns: %s \n", pronouns.data);
  
  
  FreeWordList( &adverbs );
  FreeWordList( &determiners );
  FreeWordList( &predicates );
  FreeWordList( &pronouns );
  FreeWordList( &adjectives );
  FreeWordList( &propernouns );
  FreeWordList( &verbs );
  FreeWordList( &nouns );
  FreeWordList( &conjunctions );
  FreeWordList( &interjections );
  FreeWordList( &prepositions );
  
  //--
  
  fclose(input);    
  
  return(retcode);
}






//======================================== SUBROUTINES ==================================





void analize_utterance(char *info) {

 /*
  1) copy to working buffer
  2) lowercase
  3) break into words
  4) determine sentence type
  5) 
 
 */


//----------------------------------

   
   // variables for word searching 
   char * src;
   char *words[1024];    // word pointers
   char **word;        // pointer to above array
   
   // utterance structure
   char structure[1024];
   
   int newWord;   // parser flag
   int parseStop; // parser flag

   int wordCount;
   
   // variables for looking for word types
   char tempWord[55]; // longest english 'word' + 3
   
   enum _sentenceType { Unknown, Interjection, Interrigation, Statement };
   typedef enum _sentenceType  sentenceType;

   int adjFlag, known;      

//----------------------------------
  char * tempbuff;
  
  printf("[1] -> %s", info);
//  printf("[2] Allocating %d + 2 bytes...\n", (strlen(info)));
  
  if ((tempbuff = (char *)malloc( strlen(info)+2 )) == NULL) {
    printf("MEMORY ALLOC FAILURE!\n");
  }
  
//  printf("[3] Allocation complete. Copying string...\n");
  
  strcpy(tempbuff, info);
    
//  printf("[4] Copied %d bytes. Converting case...\n", strlen(tempbuff));
  
  /* convert to lower case */
  for(src = tempbuff; *src != '\0'; src++)  {  // optimize later
     *src = lowchar(*src);
  }  
  
//  printf("[5] Conversion of %d bytes complete.\n", strlen(tempbuff));
//  printf("[6] -> %s", tempbuff);
//  printf("[7] Cracking words...\n");

  sentenceType  sentenceIsA = Unknown;

////------------------------------------------------------
   
  // one pass word cracker 
     src       = tempbuff;     // point to the first character in the string
     word      = words;    // point to the first word 
     newWord   = TRUE ; 
     parseStop = FALSE;
     wordCount = 0;
     do {
       switch (*src) {
         
        //   we need to figure out what to do with non-character things, like apostrophies, commas, and 
        //   especially periods....
        //   it woudl be wise to be able to do expansions can't -> can not        teh -> the
        //   empoy the CES libraries?
         
       
         case ' ':
         case '`':
         case '~':
         case '!':
         case '@':
         case '#':
         case '$':
         case '%':
         case '^':
         case '&':
         case '*':
         case '(':
         case ')':
         case '-':
         case '_':
         case '+':
         case '=':
         case '[':
         case ']':
         case '{':
         case '}':
         case ';':
         case ':':
         case '\'':
         case '"':
         case ',':
         case '.':
         case '/':
         case '<':
         case '>':
         case '?':
         case '\\':
         case '|':  
         case '\n':          
//           printf("[7.5] breaking on character '%c'\n", *src);               
           *src = '\0';
           newWord = TRUE;           
           break;
         
         case '\0':
//           printf("[7.5] stopping parse after %s\n", *(word-1));
           *word = src;
           word++;
           parseStop++;
           break;
         
         default:
           if (newWord) {  // mark new word
//             printf("[7.5] starting word %d at '%c'\n", wordCount,  *src);
             *word = src; 
             word++;
             wordCount++;
           }  
           newWord = FALSE;
           break;         
           
       }
       src++;
     } while( !parseStop );
     
     // work out addressing 
     
     //!!!???!!!
     
     // what type of sentence is it? 
     
     
     adjFlag = FALSE;
     structure[0] = '\0';
     wordCount = 0;
     
     for (word = words; **word != '\0'; word++) {
        
        // tempword = " **** \0";
        *tempWord = ' ';
        strncpy( tempWord+1, *word, 51 );
        *(tempWord + strlen(*word) + 1) = ' ';
        *(tempWord + strlen(*word) + 2) = '\0'; 
         
        printf("[8] Word ->%s<- ", tempWord);

        known  = FALSE;


        // gueses
        if ( (adjFlag == TRUE) ) {
          printf("?(pro)noun? ");
          adjFlag = FALSE;
        }
                
        // knowns
        
        if ( ADVERB(tempWord) ) {
          printf("adverb [verb modifier] ");
          structure[wordCount] = 'A'; wordCount++;
          known  = TRUE;
        }      
        
        if ( DETERMINER(tempWord) ) {
          printf("determiner [limit noun meaning] ");
          structure[wordCount] = 'D'; wordCount++;
          known  = TRUE;
        }      
        
        if ( PREDICATE(tempWord) ) {
          printf("predicate [quantity] ");
          structure[wordCount] = 'P'; wordCount++;
          known  = TRUE;
        }
        
        if ( PRONOUN(tempWord) ) {
          printf("pronoun [noun representitive] ");
          structure[wordCount] = 'p'; wordCount++;
          known  = TRUE;
        }
        
        if ( ADJECTIVE(tempWord) ) {
          printf("adjective [ (pro)noun next?? ] "); //[add property to noun or pronoun] ");
          structure[wordCount] = 'a'; wordCount++;
          adjFlag = TRUE;
          known  = TRUE;
        }
        
        if ( PROPERNOUN(tempWord) ) {
          printf("propernoun [object instance] ");
          structure[wordCount] = 'n'; wordCount++;
          known  = TRUE;
        }
        
        if ( VERB(tempWord) ) {
          printf("verb [action, state] ");
          structure[wordCount] = 'V'; wordCount++;
          known  = TRUE;
        }
        
        if ( NOUN(tempWord) ) {
          printf("noun [object] ");
          structure[wordCount] = 'N'; wordCount++;
          known  = TRUE;
        }
        
        if ( CONJUNCTION(tempWord) ) {
          printf("conjunction [relational] ");
          structure[wordCount] = 'C'; wordCount++;
          known  = TRUE;
        }
        
        if ( INTERJECTION(tempWord) ) {
          printf("interjection [interruption] ");
          structure[wordCount] = 'I'; wordCount++;
          known  = TRUE;
        }
        
        if ( PREPOSITION(tempWord) ) {
          printf("preposition [relation before (pro)noun ] ");
          structure[wordCount] = 'R'; wordCount++;
          known  = TRUE;
        }
        
        if (known == FALSE) {
          structure[wordCount] = '?'; wordCount++;
        }
        
        printf("\n");
       
     }
     
     structure[wordCount] = '\0';
     
     printf("[8.5] Structure is: %s \n", structure);
//         printf("%s \n", structure);

      
      // tripplet search
      if ((src = strstr( structure,   "p?a" )) != NULL) { //pVa
        printf("[8.6] pVa Adding found verb (action/state):  %s \n", words[src - structure + 1]);
//        AddWord( &verbs, words[src - structure + 1]);
      }
      if ((src = strstr( structure,   "p?p" )) != NULL) { //pVp
        printf("[8.6] pVp  Adding found verb (action/state):  %s\n", words[src - structure + 1]);
//        AddWord( &verbs, words[src - structure + 1]);
      }
      if ((src = strstr( structure,   "V?V" )) != NULL) { //VaV or VpV
        printf("[8.6] VaV Think I found a adjective or pronoun : %s\n", words[src - structure + 1]);
      }
      if ((src = strstr( structure,   "a?a" )) != NULL) { //aVa
        printf("[8.6] aVa Adding found verb (action/state):  %s\n", words[src - structure + 1]);
//        AddWord( &verbs, words[src - structure + 1]);
      }
      if ((src = strstr( structure,   "a?p" )) != NULL) { //app
        printf("[8.6] app Adding found (pro)noun:  %s\n", words[src - structure + 1]);
//        AddWord( &pronouns, words[src - structure + 1]);
      }
      if ((src = strstr( structure,   "C?V" )) != NULL) { //CpV or CaV
        printf("[8.6] CpV Think I found a pronoun or adjective:  %s\n", words[src - structure + 1]);
      }
      if ((src = strstr( structure,   "A?a" )) != NULL) { //AVa
        printf("[8.6] AVa Adding found verb (action/state):  %s\n", words[src - structure + 1]);
//        AddWord( &verbs, words[src - structure + 1]);
      }
      if ((src = strstr( structure,   "A?p" )) != NULL) { //AVp
        printf("[8.6] AVp Adding found verb (action/state):  %s\n", words[src - structure + 1]);
//        AddWord( &verbs, words[src - structure + 1]);
      }

     
//     printf("[9] Freeing buffer...\n");
     
     free(tempbuff);
     
//     printf("[10] Done.\n");
     
     return;            
}



