home *** CD-ROM | disk | FTP | other *** search
/ Power Programming / powerprogramming1994.iso / progtool / educaton / inf_src.arc / RULECOMP.C < prev    next >
C/C++ Source or Header  |  1986-03-14  |  10KB  |  374 lines

  1.  
  2. /*****************************************************************
  3. **                                **
  4. **      Inference -- (C) Copyright 1985 George Hageman    **
  5. **                                **
  6. **        user-supported software:                **
  7. **                                **
  8. **            George Hageman                **
  9. **            P.O. Box 11234                **
  10. **            Boulder, Colorado 80302            **
  11. **                                **
  12. *****************************************************************/
  13.  
  14. /*****************************************************************
  15. **    Expert system rule compiler
  16. **
  17. **    This compiler produces a file of the form:
  18. **
  19. **    Number_of_bytes_in_hypstack_section
  20. **    Hypstack_section
  21. **    Number_of_bytes_in_rule_section
  22. **    Rule base section
  23. **    Number_of_bytes_in_string_section
  24. **    String section
  25. **    EOF
  26. **    
  27. **    The rule section consits of integer flags and long-integer
  28. **    pointers to strings in the string section.
  29. **    
  30. **    All strings in the string section will be unique nomatter how
  31. **    many times they are repeated in the rules which are compiled
  32. **    into the rule base by this compiler.
  33. **
  34. **
  35. **    Usage:
  36. **
  37. **    rulecomp rule.file object.file
  38. **
  39. *****************************************************************/
  40.  
  41. /*****************************************************************
  42. **
  43. **    rule compiler main routine
  44. **
  45. *******************************************************************/
  46.  
  47. #include <stdio.h>
  48. #include <string.h>
  49.  
  50. #include "expert.h"
  51. #include "keywords.h"
  52.  
  53. int    main(argc,argv)
  54. int argc ;
  55. char **argv ;
  56.  
  57. {
  58. char    strBuff[MAX_STRING_BUFF] ;
  59. int    i ;
  60. int    state ;
  61. int    strAddr;
  62. int    numHypot, hypStack[MAX_HYPS],strBuffOfst ;
  63. int    c ;
  64. int    ruleBuffOfst ;
  65. int    keyWrdNum ;
  66. int    getKewWord() ;
  67. int    putString() ;
  68. int    lineNum ;
  69.  
  70. struct  rule_statement_r ruleBuff[MAX_RULE_STATEMENTS] ;
  71.  
  72. int    done ;
  73. FILE    *infile, *outfile ;
  74.  
  75. for( done = 0; done < MAX_STRING_BUFF; done ++ )
  76.     strBuff[done] = 0 ;
  77. for( done = 0; done < MAX_HYPS ; done++ )
  78.     hypStack[done]=0 ;
  79. done = FALSE ;
  80.  
  81. #ifdef    DEBUG
  82.     fprintf(stdout,"\nDEBUG-RULECOMP argc=%d ",argc) ;
  83. #endif
  84.  
  85. if(argc != 3 )
  86.     {
  87.     fprintf(stdout, "\n\n Usage: rulecomp in.file out.file\n\n" ) ;
  88.     exit() ;
  89.     }
  90. infile = fopen( argv[1], "r" );
  91. if(infile == NULL)
  92.     {
  93.     fprintf(stdout,"\n\n Cannot open input file %s ", argv[1]);
  94.     exit() ;
  95.     }
  96. outfile = fopen(argv[2], "wb" ) ;
  97. if(outfile == NULL)
  98.     {
  99.     fprintf(stdout,"\n\n Cannot open output file %s ",argv[2]);
  100.     exit() ;
  101.     }
  102. done = FALSE ;
  103.  
  104. numHypot = 0 ;                /* number of hypothesis is zero */
  105. strBuffOfst = 0 ;            /* pointer in buffer is zero */
  106. ruleBuffOfst = 0 ;            /* rule buffer offset is zero */
  107.  
  108.  
  109. state = ANTECEDENT ;
  110.  
  111. /* Compilation states:
  112. **
  113. **    Antecedent group in progress -- 1
  114. **    Consequent group in progress -- 2
  115. **
  116. **    If state 1 and you get a consequent then output group barrier.
  117. **        change state to 2.
  118. **    If state 2 and you get an antecedent then output group barrier.
  119. **        change state to 1.
  120. */
  121. lineNum = 1 ;
  122. printf("\n") ;
  123. while( !done )
  124.     {
  125.  
  126. /*
  127. **       get the key word number from the
  128. **    input file
  129. */
  130.     printf("%04d  ",lineNum++) ;
  131.     keyWrdNum = getKeyWord(infile,keyWords,&lineNum);
  132. /*
  133. **    error occured on line clear the line and
  134. **    start over.
  135. */
  136.     if(keyWrdNum == KEY_EOF)
  137.         {
  138.         done = TRUE ;
  139.         continue ;
  140.         }
  141.     if(keyWrdNum == KEY_WORD_ERROR)
  142.         {
  143.         while( ( (c = getc(infile))) != EOL && (c != EOF) )
  144.             putchar(c) ;
  145.         fprintf(stdout," **** KEY WORD not found on line " );
  146.         if(c == EOF)
  147.             {
  148.             done = TRUE ;
  149.             break ;
  150.             }
  151.         putchar(c) ;
  152.         continue;
  153.         }
  154. #ifdef    DEBUG
  155.     fprintf(stdout,"\nDEBUG-RULECOMP keyWrdNum = %d",keyWrdNum ) ;
  156. #endif
  157. /*
  158. **    based on the key Word build the
  159. **    rule files
  160. */
  161.  
  162.     switch(keyWrdNum)
  163.         {
  164.         case AND_N :
  165.         case ANDIF_N :
  166.         case IF_N :
  167. #ifdef    DEBUG
  168.     fprintf(stdout,"\nDEBUG-RULECOMP case AND_N, ANDIF_N, IF_N ") ;
  169. #endif
  170.             if(state == CONSEQUENT)
  171.                 {
  172.                 state = ANTECEDENT ;
  173.                 ruleBuff[ruleBuffOfst].flag = NULL ;
  174.                 ruleBuff[ruleBuffOfst++].string = NULL ;
  175.                 }
  176.             ruleBuff[ruleBuffOfst].flag = STRING_TRUE ;
  177.             strAddr=putString(infile,strBuff,&strBuffOfst) ;
  178.             ruleBuff[ruleBuffOfst++].string = strAddr ;
  179. #ifdef    DEBUG
  180.     fprintf(stdout,"\nDEBUG-RULECOMP strAddr= %d",strAddr ) ;
  181. #endif
  182.             break ;
  183.         case ANDRUN_N :
  184.         case ANDIFRUN_N :
  185.         case IFRUN_N :
  186. #ifdef    DEBUG
  187.     fprintf(stdout,"\nDEBUG-RULECOMP case AND_N, ANDIF_N, IF_N ") ;
  188. #endif
  189.             if(state == CONSEQUENT)
  190.                 {
  191.                 state = ANTECEDENT ;
  192.                 ruleBuff[ruleBuffOfst].flag = NULL ;
  193.                 ruleBuff[ruleBuffOfst++].string = NULL ;
  194.                 }
  195.             ruleBuff[ruleBuffOfst].flag = ROUTINE_TRUE ;
  196.             strAddr=putString(infile,strBuff,&strBuffOfst) ;
  197.             ruleBuff[ruleBuffOfst++].string = strAddr ;
  198. #ifdef    DEBUG
  199.     fprintf(stdout,"\nDEBUG-RULECOMP strAddr= %d",strAddr ) ;
  200. #endif
  201.             break ;
  202.         case ANDNOT_N :
  203.         case IFNOT_N  :
  204. #ifdef    DEBUG
  205.     fprintf(stdout,"\nDEBUG-RULECOMP case ANDNOT_N, IFNOT_N    ") ;
  206. #endif
  207.             if(state == CONSEQUENT)
  208.                 {
  209.                 state = ANTECEDENT ;
  210.                 ruleBuff[ruleBuffOfst].flag = NULL ;
  211.                 ruleBuff[ruleBuffOfst++].string = NULL ;
  212.                 }
  213.             ruleBuff[ruleBuffOfst].flag = STRING_FALSE ;
  214.             strAddr=putString(infile,strBuff,&strBuffOfst) ;
  215.             ruleBuff[ruleBuffOfst++].string = strAddr ;
  216. #ifdef    DEBUG
  217.     fprintf(stdout,"\nDEBUG-RULECOMP strAddr=%d",strAddr) ;
  218. #endif
  219.             break ;
  220.         case ANDNOTRUN_N :
  221.         case IFNOTRUN_N  :
  222. #ifdef    DEBUG
  223.     fprintf(stdout,"\nDEBUG-RULECOMP case ANDNOT_N, IFNOT_N    ") ;
  224. #endif
  225.             if(state == CONSEQUENT)
  226.                 {
  227.                 state = ANTECEDENT ;
  228.                 ruleBuff[ruleBuffOfst].flag = NULL ;
  229.                 ruleBuff[ruleBuffOfst++].string = NULL ;
  230.                 }
  231.             ruleBuff[ruleBuffOfst].flag = ROUTINE_FALSE ;
  232.             strAddr=putString(infile,strBuff,&strBuffOfst) ;
  233.             ruleBuff[ruleBuffOfst++].string = strAddr ;
  234. #ifdef    DEBUG
  235.     fprintf(stdout,"\nDEBUG-RULECOMP strAddr=%d",strAddr) ;
  236. #endif
  237.             break ;
  238.         case ANDTHEN_N :
  239.         case THEN_N :
  240.         case THENHYP_N :
  241.         case ANDTHENHYP :
  242. #ifdef    DEBUG
  243.     fprintf(stdout,"\nDEBUG-RULECOMP case ANDTHEN_N,THEN_N,THENHYP_N");
  244. #endif
  245.             if(state == ANTECEDENT)
  246.                 {
  247.                 state = CONSEQUENT ;
  248.                 ruleBuff[ruleBuffOfst].flag = NULL ;
  249.                 ruleBuff[ruleBuffOfst++].string = NULL ;
  250.                 }
  251.  
  252.             if( (keyWrdNum == THENHYP_N) || (keyWrdNum == ANDTHENHYP) )
  253.                 ruleBuff[ruleBuffOfst].flag = STRING_TRUE_HYP ;
  254.             else
  255.                 ruleBuff[ruleBuffOfst].flag = STRING_TRUE ;
  256.  
  257.             strAddr=putString(infile,strBuff,&strBuffOfst) ;
  258.             hypStack[numHypot++] = ruleBuffOfst ;
  259.             ruleBuff[ruleBuffOfst++].string = strAddr ;
  260. #ifdef    DEBUG
  261.     fprintf(stdout,"\nDEBUG-RULECOMP strAddr=%d",strAddr) ;
  262. #endif
  263.             break ;
  264.         case ANDTHENRUN_N :
  265.         case THENRUN_N :
  266.         case THENRUNHYP_N :
  267.         case ANDTHENRUNHYP_N :
  268. #ifdef    DEBUG
  269.     fprintf(stdout,"\nDEBUG-RULECOMP case ANDTHEN_N,THEN_N,THENHYP_N");
  270. #endif
  271.             if(state == ANTECEDENT)
  272.                 {
  273.                 state = CONSEQUENT ;
  274.                 ruleBuff[ruleBuffOfst].flag = NULL ;
  275.                 ruleBuff[ruleBuffOfst++].string = NULL ;
  276.                 }
  277.  
  278.             if( (keyWrdNum == THENRUNHYP_N ) || (keyWrdNum == ANDTHENRUNHYP_N) )
  279.                 ruleBuff[ruleBuffOfst].flag = ROUTINE_TRUE_HYP ;
  280.             else
  281.                 ruleBuff[ruleBuffOfst].flag = ROUTINE_TRUE ;
  282.  
  283.             strAddr=putString(infile,strBuff,&strBuffOfst) ;
  284.             hypStack[numHypot++] = ruleBuffOfst ;
  285.             ruleBuff[ruleBuffOfst++].string = strAddr ;
  286. #ifdef    DEBUG
  287.     fprintf(stdout,"\nDEBUG-RULECOMP strAddr=%d",strAddr) ;
  288. #endif
  289.             break ;
  290.         case KEY_EOF :
  291. #ifdef    DEBUG
  292.     fprintf(stdout,"\nDEBUG-RULECOMP case KEY_EOF ") ;
  293. #endif
  294.             done = TRUE ;
  295.             break ;
  296.         default:
  297. #ifdef    DEBUG
  298.     fprintf(stdout,"\nDEBUG-RULECOMP case DEFAULT "  ) ;
  299. #endif
  300.             fprintf(stdout, " \n\n illegal keyword number found " );
  301.         }
  302.     }
  303.  
  304. /* 
  305. **    set up some blank space at the end of the rule file 
  306. */
  307.  
  308. ruleBuff[ruleBuffOfst].flag = NULL ;
  309. ruleBuff[ruleBuffOfst++].string = NULL ;
  310. ruleBuff[ruleBuffOfst].flag = NULL ;
  311. ruleBuff[ruleBuffOfst++].string = NULL ;
  312. ruleBuff[ruleBuffOfst].flag = NULL ;
  313. ruleBuff[ruleBuffOfst++].string = NULL ;
  314. if(ruleBuffOfst%2 == 0 )
  315.     {
  316.     ruleBuff[ruleBuffOfst].flag = NULL ;
  317.     ruleBuff[ruleBuffOfst++].string = NULL ;
  318.     }
  319. #ifdef    DEBUG
  320.     fprintf(stdout,"\nDEBUG-RULECOMP ruleBoffOfst=%d", ruleBuffOfst ) ;
  321. #endif
  322. /*
  323. **    ruleBuffOfst -3 is the number of rule statements processed 
  324. */
  325.  
  326. /*
  327. **
  328. **    Write out all of the compiled information as follows:
  329. **
  330. **        numHypot*2    Number_of_bytes_in_hypstack_section
  331. **        hypStack    Hypstack_section
  332. **        ruleBuffOfst    Number_of_bytes_in_rule_section
  333. **        ruleBuff    Rule base section
  334. **        strBuffOfst    Number_of_bytes_in_string_section
  335. **        strBuff        String section
  336. **        EOF
  337. **
  338. */
  339. #ifdef DEBUG
  340.  
  341.     fprintf(stdout,"\nDEBUG numHypot=%d",numHypot ) ;
  342.  
  343.     for(i=0;i<numHypot;i++)
  344.         fprintf(stdout,"\nDEBUG     hypStack=%d",hypStack[i] ) ;
  345.  
  346.     fprintf(stdout,"\nDEBUG ruleBuffOfst=%d  ",ruleBuffOfst ) ;
  347.  
  348.     for(i=0;i<ruleBuffOfst;i++)
  349.         {
  350.         fprintf(stdout,"\nDEBUG ruleBuff[%d].flag=%d ",i,ruleBuff[i].flag ) ;
  351.         fprintf(stdout,"\nDEBUG ruleBuff[%d].string=%d ",i,ruleBuff[i].string ) ;
  352.         }
  353.  
  354.     fprintf(stdout,"\nDEBUG strBuffOfst=%d",strBuffOfst ) ;
  355.  
  356.     for(i=0;i<strBuffOfst;i++)
  357.         fprintf(stdout,"\nDEBUG strBuff[%d]=%d(d),%c(c)",i,strBuff[i],strBuff[i] ) ;
  358. #endif
  359. fwrite(&numHypot,sizeof(int),1,outfile) ;
  360. fwrite(hypStack,sizeof(int),numHypot,outfile) ;
  361. fwrite(&ruleBuffOfst,sizeof(int),1,outfile) ;
  362. fwrite(ruleBuff,2*sizeof(int),ruleBuffOfst,outfile) ;
  363. fwrite(&strBuffOfst,sizeof(int),1,outfile) ;
  364. fwrite(strBuff,1,strBuffOfst,outfile) ;
  365. fclose(infile);
  366. fclose(outfile);
  367. #ifdef DEBUG
  368.     fclose(stdout) ;
  369. #endif
  370. printf("\n\n") ;
  371. exit(0) ;
  372. }
  373.  
  374.