/****************************************************************************************************************************************************************************************************************************************************************************************************** * ACS Computing competition July 1995. * * C solution to * Problem F: Symbolic AI * * Brendan Humphreys. * brendan@cssa.anu.edu.au * */ #include <stdio.h> #define FACT 256 #define IDENT 257 #define QUEST 258 #define UNKNOWN -1 struct Sident { char name[40]; int type; }; struct Snouns { char name[40]; }; struct Sverbs { char name[40]; }; struct Sfacts { int a, v, b; }; struct Sident ident[100]; /* the identity table */ struct Snouns nouns[100]; /* the noun table */ struct Sverbs verbs[100]; /* the verb table */ struct Sfacts facts[100]; /* fact/relationship table */ char input[100]; char s1[40]; char s2[40]; char s3[40]; char s4[40]; int nounindex, identindex, verbindex, factindex = 0; int gettype() { int strs; strs = sscanf(input,"%s %s %s %s",s1,s2,s3,s4); if (strs == 3) { s1[strlen(s1)-1] = '\0'; /* strip 's' */ s3[strlen(s3)-2] = '\0'; /* strip 's.' */ return FACT; } else if ((strs == 4) && (strchr(input,'?') != NULL )) { s4[strlen(s4)-1] = '\0'; /* strip '?' */ return QUEST; } else { s4[strlen(s4)-1] = '\0'; return IDENT; } } int insertnoun(const char s[]) /* if unique, inserts noun into nountable. returns index */ { int i; for ( i = 0; i <= nounindex; i++) { if ((strcmp(nouns[i].name,s) == 0)) return i; } nounindex++; strcpy(nouns[nounindex].name,s); return nounindex; } int insertverb(const char s[]) /* if unique, inserts verb into verb table. returns index */ { int i; for (i = 0; i <= verbindex; i++) { if (( strcmp(verbs[i].name,s) == 0)) return i; } verbindex++; strcpy(verbs[verbindex].name,s); return verbindex; } int insertident(const char s[], const char t[]) /* if unique, inserts ident into ident table. returns index. */ { int i; for (i = 0; i <= identindex; i++) { if (( strcmp(ident[i].name,s) == 0)) return i; } identindex++; strcpy(ident[identindex].name,s); ident[identindex].type = insertnoun(t); return identindex; } void makelower(char *s) /* convert a string to lower case */ { int i; for (i = 0; s[i] != '\0'; i++) s[i] = tolower(s[i]); } void main() { char c; int i,t; int f1,f2,f3; while (1) { /* get a line of input */ i = 0; while ((c = getchar()) != '\n' ) { input[i] = c; i = i + 1; } input[i++] ='\0'; if (input[0] == '#') /* catch the terminating condition */ exit(1); t = gettype(); /* determine the type of input, fill global strings */ makelower(s1); /* convert all global strings to lower case */ makelower(s2); makelower(s3); makelower(s4); switch ( t ) { case FACT: f1 = insertnoun(s1); /* fill up tables */ f2 = insertverb(s2); f3 = insertnoun(s3); factindex++; facts[factindex].a = f1; /* add 'fact' to fact table */ facts[factindex].v = f2; facts[factindex].b = f3; break; case IDENT: insertident(s1,s4); break; case QUEST: f1 = insertident(s2,s3); /* get individuals index in ident table */ f1 = ident[f1].type; /* use this to get its type */ f2 = insertverb(s3); /* get verb index */ f3 = insertident(s4,s3); f3 = ident[f3].type; /* check fact table to see if the entry f1,f2,f3 is present */ for (i = 1; i <= factindex; i++) { if ((facts[i].a == f1) && (facts[i].v == f2) && (facts[i].b == f3) ) { /* found it. The answer is Yes */ printf("Yes.\n"); break; } } if ( i > factindex) /* didn't find it, the answer is No */ printf("No.\n"); break; default: printf(" $ ERROR $ \n"); } } }