📄 动物识别.c
字号:
#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
#include <windows.h>
#include <math.h>
#include <string.h>
/*事实链表的结构描述*/
struct CAUSE_TYPE
{char* cause;
struct CAUSE_TYPE* next;
};
/*规则链表的结构描述*/
struct RULE_TYPE
{char *result;
int lastflag;
struct CAUSE_TYPE *cause_chain;
struct RULE_TYPE *next;
};
/*==================*/
struct CAUSE_TYPE *DataBase;
struct CAUSE_TYPE *Conclusion;
struct RULE_TYPE *KnowledgeBase;
struct RULE_TYPE *Used;
/*==================*/
void freeKB(struct RULE_TYPE *);
void freeDB(struct CAUSE_TYPE *);
int FindCause(char*);
void markKB();
void creatKB();
void inputDB();
void think();
void explain();
long FAR PASCAL_WndFun(HWND hWnd,UINT mes, WPARAM wParam,LPARAM lParam);
HANDLE hCurInst;
int PASCAL WinMain(HANDLE hInst,HANDLE hPreInst,LPSTR lpCmd,int nStyle)
{char Name[]="动物识别专家系统";
HWND hwnd;
MSG msg;
WNDCLASS wc;
hCurInst=hInst;
if(! hPreInst)
{
wc.lpszClassName=Name;
wc.hInstance=hInst;
wc.lpfnWndProc=_WndFun;
wc.hCursor=LoadCursor(0,IDC_ARROW);
wc.hIcon=LoadIcon(0,IDI_APPLICATION);
wc.lpszMenuName=0;
wc.hbrBackground=GetStockObject(WHITE_BRUSH);
wc.style=CS_HREDRAW|CS_VREDRAW;
wc.cbClsExtra=0;
wc.cbWndExtra=0;
if(! RegisterClass(&wc))
return FALSE;
}
hWnd=CreateWindow(Name,Name,WS_OVERLAPPEDWINDOW,180,120,220,250,0,0,hInst,NULL);
ShowWindow(hWnd,nStyle);
UpdateWindow(hWnd);
while(GetMessage(&msg,0,0,0))
{
TranslateMassage(&msg);
DispatchMessage(&msg);
}
return msg.wParam;
}
long FAR PASCAL_WndFun(HWND hWnd,UINT mes, WPARAM wParam,LPARAM lParam)
{
static HWND hcre,hin,hth,hex,hqu;
RECT w;
for(;;)
{
switch(mes)
{
case WM_DESTROY:
PostQuitMessage(0);
return 0;
case WM_COMMAND:
{
if(LOWORD(lParam)==hcre) creatKB();
if(LOWORD(lParam)==hin) inputDB();
if(LOWORD(lParam)==hth) think();
if(LOWORD(lParam)==hex) explain();
if(LOWORD(lParam)==hqu)
{
freeKB(KnowledgeBase);
freeKB(Used);
freeDB(DataBase);
freeDB(Conclusion);
DestroyWindow(hWnd);
PostQuitMessage(0);
}
return(0);
}
case WM_CREATE:
GetClientRect(hWnd,&w);
hcre=CreateWindow("BUTTON","创建知识 库",WS_CHILD|WS_VISIBLE|BS_PUSHBUTTON,40,30,100,25,hWnd,0,hCurInst,0);
hin=CreateWindow("BUTTON","输入已知事 实",WS_CHILD|WS_VISIBLE|BS_PUSHBUTTON,40,60,100,25,hWnd,1,hCurInst,0);
hth=CreateWindow("BUTTON","进行推 理",WS_CHILD|WS_VISIBLE|BS_PUSHBUTTON,40,90,100,25,hWnd,2,hCurInst,0);
hex=CreateWindow("BUTTON","解 释",WS_CHILD|WS_VISIBLE|BS_PUSHBUTTON,40,120,100,25,hWnd,3,hCurInst,0);
hqu=CreateWindow("BUTTON","退 出",WS_CHILD|WS_VISIBLE|BS_PUSHBUTTON,40,150,100,25,hWnd,4,hCurInst,0);
return 0;
default:
returnDefWindowProc(hWnd,mes,wParam,lParam);
}
}
}
/*释放条件链表*/
void freeDB(struct CAUSE_TYPE *cPoint)
{
struct CAUSE_TYPE *cp;
while(cPoint)
{
cp=cPoint->next;
free(cPoint->cause);
cPoint->cause=NULL;
cPoint->next=NULL;
free(cPoint);
cPoint=cp;
}
}
/*释放规则链表*/
void freeKB(struct RULE_TYPE *rPoint)
{
struct RULE_TYPE *rp;
while(rPoint)
{
rp=rPoint->next;
free(rPoint->cause_chain);
rPoint->cause_chain=NULL;
free(rPoint->result);
rPoint->result=NULL;
rPoint->next=NULL;
free(rPoint);
rPoint=rp
}
}
/*整理输入的规则,找出结论性的规则并打上标记*/
void markKB()
{
struct RULE_TYPE *rp1,rp2;
struct CAUSE_TYPE *cp;
rp1=KnowledgeBase;
while(rp1)
{
cp=rp1->cause_chain;
rp1->lastflag=1;
while(cp)
{
rp2=KnowledgeBase;
while(rp2)
{
if(strcmp(rp2->result,cp->cause)==0)
rp2->lastflag=0;
rp2=rp2->next;
}
cp=cp->next;
}
rp1=rp1->next;
}
}
/*创建知识库*/
void creatKB()
{
FILE *fp;
struct CAUSE_TYPE *cp=NULL;
struct RULE_TYPE *rp=NULL;
int i,j;
char sp[80];
char ch;
freeKB(KnowledgeBase);
freeKB(Used);
KnowledgeBase=Used=NULL;
if((fp=fopen(".\\rule.dat","r"))==NULL)
{
printf("\n 知识库不存在!\n");
printf("请输入新的规则,以创建知识库!\n");
for(i=1;;i++)
{
printf("\n********第(%d)条规则********",i);
printf("\n**结论:(是/会/有)");
gets(sp);
if(*sp=='\0') break;
rp=(struct RULE_TYPE *) malloc(sizeof(rp));
rp->result=(char*) malloc(sizeof(sp));
strcpy(rp->result,sp);
rp->cause_chain=NULL;
rp->next=KnowledgeBase;
KnowledgeBase=rp;
for(j=1;;j++)
{
printf("\n***条件(%d):(是/会/有)",j);
gets(sp);
if(*sp=='\0') break;
cp=(struct CAUSE_TYPE *) malloc(sizeof(cp));
cp->cause=(char*) malloc(sizeof(sp));
strcpy(cp->cause,sp);
cp->next=rp->cause_chain;
rp->cause_chain=cp;
}
}
if(! KnowledgeBase)
{
printf("\n警告!知识库中没有任何规则!!\n");
return;
}
printf("\n需要保存已建立的知识库吗?(Y/N)?");
while(! strchr("YyNn",ch=getchar()));
if (ch=='Y'|ch=='y')
if((fp==fopen(".\\rule.dat","w"))==NULL)
{
printf("\n写文件有错误!\n");
exit(1);
}
else{
/*保存已建立的知识库*/
rp=KnowledgeBase;
while(rp)
{
fputs(rp->result,fp);
fputc('\n',fp);
cp=rp->cause_chain;
while(cp)
{
fputs(cp->cause,fp);
fputc('\n',fp);
cp=cp->next;
}
fclose(fp);
}
}
else{
while(! feof(fp))
{
fgets(sp,80,fp);
if(*sp=='\\') break;
rp=(struct RULE_TYPE *) malloc(sizeof(rp));
rp->result=(char *) malloc(i=strlen(sp));
sp[i-1]='\0';
strcpy(rp->result,sp);
rp->cause_chain=NULL;
rp->next=KnowledgeBase;
KnowledgeBase=rp;
fgets(sp,80,fp);
while(*sp!='\\')
{
cp=(struct CAUSE_TYPE * ) malloc(sizeof(cp));
cp->cause=(char *) malloc(i=strlen(sp));
sp[i-1]='\0';
strcpy(cp->cause,sp);
cp->next=cp->cause_chain;
rp->cause_chain=cp;
fgets(sp,80,fp);
}
}
fclose(fp);
}
markKB();
}
void inputDB()
{
int i;
char sp[80];
struct CAUSE_TYPE *cp;
freeDB(DataBase);
freeDB(Conclusion);
DataBase=Conclusion=NULL;
printf("\n*****请输入已知事实:\n");
for(i=1;;i++)
{
printf("\n**条件(%d):(是/会/有)",i);
gets(sp);
if(*sp=='\0') break;
cp=(struct CAUSE_TYPE *) malloc(sizeof(cp));
cp->cause=(char *) malloc(sizeof(sp));
strcpy(cp->cause,sp);
cp->next=DataBase;
DataBase=cp;
}
}
int FindCause(char *sp)
{
struct CAUSE_TYPE *cp2;
cp2=DataBase;
while(cp2)
if(strcmp(sp,cp2->cause)==0 return(1);
else cp2=cp2->next;
cp2=Conclusion;
while(cp2)
if(strcmp(sp,cp2->cause)==0 return(1);
else cp2=cp2->next;
return (0);
}
void think()
{
struct RULE_TYPE *rp1,*rp2;
struct CAUSE_TYPE *cp1;
int RuleCount,i;
char sp[80];
if(Used)
{
rp1=Used;
while(rp1->next) rp1=rp1->next;
rp1->next=KnowledgeBase;
KnowledgeBase=Used;
Used=NULL;
}
if(Conclusion)
{
freeDB(Conclusion);
Conclusion=NULL;
}
do{
RuleCount=0;
rp1=KnowledgeBase;
while(rp1)
{
cp1=rp1->cause_chain;
while(cp1)
if(FindCause(cp1->cause)==0)
break;
else cp1=cp1->next;
if(cp1)
{
rp2=rp1;
rp1=rp1->next;
}
else if(FindCause(rp1->result)==0)
{
cp1=(struct CAUSE_TYPE *) malloc(sizeof(cp1));
cp1->cause=(char*) malloc(sizeof(rp1->result));
strcpy(cp1->cause,rp1->result);
cp1->next=Conclusion;
Conclusion=cp1;
rp2->next=rp1->next;
rp1->next=Used;
Used=rp1;
rp1=rp2;
RuleCount++;
if(Used->lastflag==1)
{
RuleCount=0;
break;
}
}
else{
rp2=rp1;
rp1=rp1->next;
}
}
}while(RuleCount>0);
if(!Conclusion||Used->lastflag==0)
{
printf("\n已知事实不充分!请输入补充事实:\n");
cp1=DataBase;
for(i=1;cp1;i++)
{
printf("\n**条件(%d):(是/会/有) %s",i,cp1->cause);
cp1=cp1->next;
}
for(;;i++)
{
printf("\n**条件(%d):(是/会/有) %s",i);
gets(sp);
if(*sp=='\0') break;
cp1=(struct CAUSE_TYPE *) malloc(sizeof(cp1));
cp1->cause=(char *) malloc(sizeof(sp));
strcpy(cp1->cause,sp);
cp1-next=DataBase;
DataBase=cp1;
}
}
else printf("\n这个动物::(是/会/有)\"%s\"\n",Conclusion->cause);
}
void explain()
{
struct RULE_TYPE *rp;
struct CAUSE_TYPE *cp;
int i;
rp=Used;
i=0;
while(rp)
{
printf("\n这个动物(是/会/有)\"%s\",因为:\n",rp->result);
cp=rp->cause_chain;
while(cp)
{
printf("**这个动物(是/会/有)\"%s\"\n",i++,cp->cause);
cp=cp->next;
}
rp=rp->next;
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -