产生式规则实现动物、手机识别系统

一. 实验目的

基于产生式规则建立一个手机识别系统,主要功能如下:
(1)建造规则库,并基于该库进行手机品牌的识别推理;
(2)对规则库进行增加、删除和修改操作。

系统所需规则文件可通过产生式系统(包含动物识别规则库,手机识别规则库以及产生式系统的python语言程序)下载,文件包含动物识别规则库及手机识别规则库 ,在初始规则库部分导入不同的文件可实现不同的识别系统

二. 实验原理

基于某些物品的独有特征建立知识库,用一阶谓词逻辑和产生式规则作为知识表示,应用这些知识表示,实现用户输入特征与知识库中规则的产生式推理。如规则为:IF x THEN y,则当输入特征与x匹配时,推出y这一结果。
推理过程中,将事实与知识库匹配,依据不同情况,应用字符串匹配或模糊匹配实现事实的推理并输出推理结果,同时可以进行反向推理,用户输入结果,系统通过与事实库中结果的字符串匹配来返回该结果的特征。

三. 实验过程

1. 事实库建立

建立手机品牌及型号的知识库,将初始知识写入excel表格中,其中条件在一列,结果在一列,表格具体如下。
手机识别规则库
将该存储该文件的表命名为“df”,excel文件命名为“手机识别规则库.xlsx”,规则库建立成功。

2. 程序编写

2.1 事实库拆分模块

将事实库分为类别规则库与名称规则库,分类原理为:若事实库中某规则的结果在另一个规则的条件中出现,则将该规则加入到类别规则库中,若在所有规则的条件中都不存在,则将其加入到名称规则库中,直到所有的规则都与除自己外的其它规则比较,拆分过程结束。具体代码如下。

'''定义特征分类函数'''
def cut(df):  
    x = 0
    y = 0
    flagnum = ""
    for i in range(df.shape[0]):        
        flag = df.iloc[i, 0]
        flagnum = str(flagnum) + ',' + flag 
    for i in range(df.shape[0]):
        flag = df.iloc[i, 0]
        result = df.iloc[i, 1]
        if result in flagnum:
            df1.loc[x] = [flag, result]
            x = x + 1           
        else:
            df2.loc[y] = [flag, result]
            y = y + 1
    return df1, df2

2.2 正向推理模块

首先将事实与类别规则库匹配,只要输入的事实与类别规则的特征匹配就判定事实属于该类别,并将该类别添加到事实中;在事实与类别规则库中所有规则匹配结束后,将更新后的事实与名称规则库中所有规则匹配,利用python中的fuzz.partial_ratio函数得到匹配的相似度值,最终返回相似度值最大的规则的结果作为识别结果。
同时,在程序设计时,考虑到用户输入特征过少造成匹配结果极差的可能,对输入特征的个数进行判断,预设初始最少输入特征为四个,当输入少于四个时,则让用户继续添加特征。在识别结果上,如果最后得到的相似度值过低,则返回“结果可能为:”这样的语句,具体代码如下。

'''定义识别模块'''
def identify(df1, df2):
    '''类别规则库识别'''
    starttemp = input("请输入要识别的特征(以,分隔):\n")
    temp = starttemp
    temp1 = re.sub(r'[色, 物, 有, 子, 会]', "", temp)
    for i in range(df1.shape[0]):
        flag = df1.iloc[i, 0]
        addword(flag)
        result = df1.iloc[i, 1]
        addword(result)
        temp0 = jieba.lcut(temp1)
        for j in range(len(temp0)):
            if temp0[j] in re.sub(',', "", flag) and re.sub(',', "", result) not in temp:  
                temp = temp + ',' + re.sub(',', "", result)
                print("类别库规则r" + str(i) + ":IF " + flag + " THEN 为" + result + "匹配成功,\
                      \n更新事实为:" + temp + '\n')
    if temp == starttemp:
        print("未在类别库中找到这些特征,继续识别的结果可能不准确。")
    '''名称规则库识别'''    
    while(len(temp.split(',')) < 4):
        te = input("特征过少,请继续添加特征:\n")
        if te in temp:
            print("特征重复,请重新输入!")
        else:
            temp = temp + ',' + te
    temp1 = re.sub(r'[色, 物, 有, 子, 会]', "", temp)
    temp0 = jieba.lcut(temp1)
    n = 0
    num = 0
    for i in range(df2.shape[0]):
        flag = df2.iloc[i, 0]
        addword(flag)
        result = df2.iloc[i, 1]
        addword(result)
        m = 0
        for j in range(len(temp0)):   
            m = m + fuzz.partial_ratio(temp0[j], re.sub(',', "", flag))
        if num < m:
            num = m
            n = i   
    flag0 = df2.iloc[n, 0]
    result0 = df2.iloc[n, 1]
    if num == 0:
        print("抱歉,识别失败,请等待后续规则库完善。")
    else:
        print("名称库规则r" + str(n) + ':IF ' + flag0 + " THEN 为" + result0 + "匹配成功,")
        if num < 600:
            print("结果可能为:" + result0)
        else:
            print("推出结果为:" + result0)

2.3 反向推理模块

将用户输入的结果先与名称规则库中的结果进行匹配,若匹配成功,则将该结果所对应的特征输出,并将该特征添加到结果中。名称规则库匹配完成后,将更新后的结果与类别规则库中的结果进行匹配,若匹配成功,则将该结果所对应的特征输出,并将该特征添加到结果中,直到结果与类别库中所有规则匹配成功。在进行完两轮匹配操作后,若更新后的结果等于初始输入的结果,则说明该结果在事实库中不存在,输出“该结果在规则库中匹配失败,请等待后续规则库完善。”反向推理模块的具体代码如下。

'''定义规则输出模块'''
def rule(df1, df2):
    starttemp = input("请输入要输出特征的结果:\n")
    temp = starttemp
    for i in range(df2.shape[0]):
        flag = df2.iloc[i, 0]
        result = df2.iloc[i, 1]
        if starttemp in result or result in starttemp:
            print("名称库规则r" + str(i) + ":IF " + flag + " THEN 为" + result + "匹配成功,\
                  \n得到结果" + starttemp + "的特征为:" + flag)
            temp = starttemp + ',' + flag
    for i in range(df1.shape[0]):
        flag = df1.iloc[i, 0]
        result = df1.iloc[i, 1]
        if temp in result or result in temp:
            print("类别库规则r" + str(i) + ":IF " + flag + " THEN 为" + result + "匹配成功,\
                  \n得到结果" + starttemp + "的特征为:" + flag)
            temp = temp + ',' + flag
    if temp == starttemp:
        print("该结果在规则库中匹配失败,请等待后续规则库完善。")

2.4 规则更新模块

更新模块包括修改、增加和删除三个功能。
规则增加功能需获取用户输入的规则,并将该规则添加到规则库中。修改和删除功能获取用户输入的要修改或删除的规则的结果,并将该输入与原始规则库进行匹配,若匹配成功则进行规则的更新,否则让用户重新进行输入,这些功能具体代码如下。

'''定义规则增加模块'''        
def insert(df, excelFile):
    f = 1
    while(f == 1):
        flag0 = input("请输入要添加的特征:\n")
        result0 = input("请输入要添加的结果:\n")
        resultnum = ""
        flagnum = ""
        for i in range(df.shape[0]):
            flag = df.iloc[i, 0]
            flagnum = flagnum + ',' + flag         
            result = df.iloc[i, 1]
            resultnum = resultnum + ',' + result 
        if result0 in resultnum:
            print("当前结果已在规则库中存在,请重新添加或选择修改该结果的特征!")
        else:
            df.loc[len(df)] = [flag0, result0]
            print("该规则添加成功,", end = '')
        print("要继续添加吗?(yes or no)")
        a = input()
        if a == "no":
            break     
    df.to_excel(excelFile, sheet_name='df', index = False)
    
'''定义规则修改模块'''      
def update(df, excelFile):  
    f = 1
    while(f == 1):
        f1 = 0
        result0 = input("请输入要修改的规则的结果:\n")
        for i in range(df.shape[0]):
            flag = df.iloc[i, 0]
            result = df.iloc[i, 1]
            if result0 == result:
                print("当前规则为:IF " + flag + " THEN " + result)
                flag = input("请输入修改后的规则的特征:\n")
                df.loc[i] = [flag, result]
                f1 = 1
                print("该规则修改成功,", end = '')
                break     
        if f1 == 0:
            print("该规则不存在", end = ',')
        print("要继续修改吗?(yes or no)")
        a = input()
        if a == "no":
            break
    df.to_excel(excelFile, sheet_name='df', index = False)   
    
'''定义规则删除模块'''   
def delete(df, excelFile):
    f = 1
    while(f == 1):
        f1 = 0
        result0 = input("请输入要删除的规则的结果:\n")
        for i in range(df.shape[0]):          
            result = df.iloc[i, 1]
            if result0 == result:
                df = df.drop([i])
                f1 = 1
                print("该规则删除成功,", end = '')
                break   
        if f1 == 0:
            print("该规则不存在,", end = '')
        print("要继续删除吗?(yes or no)")
        a = input()
        if a == "no":
            break
    df.to_excel(excelFile, sheet_name='df', index = False)

3. 程序测试

完成事实库的文件读取的相关代码如下。

'''得到初始规则库'''
excelFile = r'手机识别规则库.xlsx'
df = pd.DataFrame(pd.read_excel(excelFile, sheet_name = 'df'))
df1 = pd.DataFrame(columns = ["flag", "result"])
df2 = pd.DataFrame(columns = ["flag", "result"])
[df1, df2] = [cut(df)[0], cut(df)[1]]

基于读入的知识库,进行上述功能的测试,并在测试过程中修改程序中的错误从而不断完善程序,以求得到最佳的识别结果及执行效率,最终的程序运行结果见“四. 实验结果”。

四. 实验结果

经过不断的程序测试与完善,最终得到该程序正向推理模块的事实库匹配成功并识别的结果如图4.1,4.2,输入的事实在规则库不存在从而匹配失败的情况如图4.3。
图4.1 正向推理成功1
图4.2 正向推理成功2
图4.3 正向推理失败
反向推理模块的事实库匹配成功的情况如图4.4,匹配失败如图4.5。
图4.4 反向推理成功图4.5 反向推理失败

五. 总结

该程序通过正则表达式,模糊匹配及中文语言分词,以求最大程度上消除用户输入必须与规则中的特征严格相同的局限,从而方便用户的使用。
在此基础上,程序实现了产生式系统的正向和反向推理
然而,作为一个产生式系统,目前只具备较低的学习能力,实现了每次读取规则库中的特征并将其添加到分词字典中,从而避免某些专有名词被拆分。但在近义词分析上,目前还不具备这样的能力,从而一定程度上局限了该产生式系统地推理效果,所以未来的改进方向将集中于此。

六. 程序补全

调用库

from fuzzywuzzy import fuzz
import pandas as pd
import re
import jieba

辅助函数

'''定义添加字典函数'''
def addword(x):
    fl = x.split(',')
    for j in range(len(fl)):
        jieba.add_word(fl[j])

主程序

print("欢迎使用" + re.sub(".xlsx", "", excelFile))
while(1):        
    flag = input("请选择要使用的功能:\n1.根据特征进行识别\n2.根据结果输出特征\n3.更新规则\n0.退出程序\n")
    if int(flag) == 1:    
        identify(df1, df2)
    elif int(flag) == 2:
        rule(df1, df2)
    elif int(flag) == 3:
        while(1):
            flag1 = input("请选择要使用的功能:\n1.删除规则\n2.修改规则\n3.添加规则\n0.退出当前菜单\n")
            if int(flag1) == 1:
                delete(df, excelFile) 
            elif int(flag1) == 2:
                update(df, excelFile)
            elif int(flag1) == 3:
                insert(df, excelFile)
            elif int(flag1) == 0:
                break
    elif int(flag) == 0:
        break

这是很久之前写的程序了,如今快毕业了,一点点分享出来,也算是对大学生活的一点点总结吧,同时希望能够帮助到学弟学妹们。
如今再看这段程序,魅蓝没了,李楠离职了,有的规则也就不适用了,真的蛮感慨的。

  • 15
    点赞
  • 63
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

lazyn

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值