教材:《人工智能及其应用》,蔡自兴等,2016m清华大学出版社(第5版)
参考书:

1 知识表示方法—渡河问题
程序执行流程:
- 首先,包含状态(首次为初始状态)的结构体结点(已存入结构体数组)传入处理函数,然后判断该传入结点状态是否为目标状态。
是则遍历打印结构体数组,打印完成之后,返回递归调用处,顺序执行之后代码(此步骤关系到是否能找到所有过河路径);
否则继续判断是否该传入结点已存在于结构体数组当中,如存在,不再往下执行,返回递归调用处,顺序执行之后代码;
若不存在,则继续判断该传入状态的人数是否合理(是否出现人物数量小于0的情况等),若不合理,返回递归调用处,顺序执行之后代码;
若合理,则继续判断传教士和野人人数限制条件,即在传教士人数不为0的情况下,野人人数是否大于传教士人数,若大于则出现吃人的情况,也就是说该传入状态也不合理,则返回递归调用处,顺序执行之后代码;
若不满足大于条件,则说明该状态是路径转态,也就是合理的,那么进行五种渡河方案的依次变换,首先为第一种渡河方案,两个传教士过河(注意:此处的5中渡河方案没有固定顺序,也可以是其他渡河方案),那么对该传入状态的左岸和右岸的传教士人数和野人人数进行增减。 - 增减完成并改变船的状态(使用正负一表示,正一为左岸,负一为右岸)以后就产生了一个新的状态,将该状态存入结构体数组,之后此处又递归调用处理函数,将新产生的转态结点传入,再次进行上述条件限制判断。
若在该判断途中被返回至递归调用处,说明该状态不合理,则此时将已经存入结构体数组的状态结点移出结构体数组,然后程序顺序执行,进行下一个渡河方案的处理,也就是说,此时的处理是对上一个传入结点的操作(因为刚传入的已经移出了);
若在判断途中未被返回至递归调用处,也就是说,传入的结点合理了,那么又开始从第一种渡河方案开始对该传入状态进行操作。 - 按照上述过程循环执行,直到出现目标状态,回到本段开头,遍历结构体数组,打印渡河路径结点信息。
- 完成以后,返回递归调用处,顺序执行之后代码,此后的操作是在寻找其他渡河路径。
程序说明:
-
结构体MyLeftBank定义传教士、野蛮人和船的状态

-
InitSailWay函数负责初始化传教士、野蛮人的数量和路线编号

-
BoatGoOppositeBank函数负责船完成一次航行后,传教士、野蛮人和船的状态转换,出错返回-1

-
JudgeBothBankState函数负责检查两岸的状况是否合法

-
ReturnAvailableState函数负责当到达目标状态时,返回可用的路线

-
PrintingSailWay函数负责输出安全渡河的方案编号和过程

-
CrossRiver函数负责统计安全渡河的方案数,如无安全渡河的方案,也给出“很遗憾,我们找不到方案”的提示

程序截图:


当m,c,n增大时,程序花费的时间大幅度增加:


2 A*算法解决8数码问题
-
估价函数f(n) = g(n) + h(n)
其中f(n)是节点n从初始点到目标点的估价函数,g(n)是在状态空间中从初始节点到n节点的实际代价,h(n)是从n到目标节点最佳路径的估计代价。
设g(n)为已经移动的步数。在move函数中,每次移动加1即可。
设h(n)为此状态与目标状态中相异数字的个数。由a_start_h函数求得:

-
open表与close表的维护
open表:可以简单认为是一个未搜索节点的表
close表:可以简单认为是一个已完成搜索的节点的表(即已经将下一个状态放入open表内)
规则一:对于新添加的节点S(open表和close表中均没有这个状态),S直接添加到open表中。
规则二:对于已经添加的节点S(open表或者close表中已经有这个状态),若在open表中,与原来的状态S_0的f(n)比较,取最小的一个。若在close表中,那就分成两种情况:第一种,close表中的该状态S_0的f(n)大于S的,不做修改;第二种S_0的f(n)小于S的,那就要需要将close表中S_0的f(n)更新,同时将该状态移入到open表中。
规则三:下一个搜索节点的选择问题,选取open表中f(n)的值最小的状态作为下一个待搜索节点
规则四:每次需要将带搜索的节点下一个所有的状态按照规则一、二更新open表,close表,搜索完该节点后,移到close表中。 -
无解情况
将九宫格变成线性后,计算初始状态和目标状态的奇偶性是否一致,一致有解,否则无解。

程序截图:
输入起始图和目标图,若有解,则输出移动过程和步数;若无解,则输出无解。

3 BP神经网络——鸢尾花识别问题
-
下载Iris数据集并导入
进入Iris Data Set下载鸢尾花数据集iris.data:

-
数据归一化
%数据归一化处理
x_max=max(data);
x_min=min(data);
data=(data-ones(m,1)*x_min)./(ones(m,1)*(x_max-x_min));
- 划分训练样本和测试样本
将Iris(鸢尾花)数据集分为训练集(Iris-train.txt)和测试集(Iris-test.txt),分别含75个样本。
%划分训练样本和测试样本 大约1/2用作训练,1/2用作测试
num=round(m/2/3);
for i=1:3
temp=data(1+50*(i-1):50*i,:);
sel=randperm(50,num);
test(1+num*(i-1):num*i,:)=temp(sel,1:4);
test_label(1+num*(i-1):num*i,:)=temp(sel,5:7);
temp(sel,:)=[];
train(1+(50-num)*(i-1):(50-num)*i,:)=temp(:,1:4);
train_label(1+(50-num)*(i-1):(50-num)*i,:)=temp(:,5:7);
end
- BP神经网络设置
alpha=4;%输入神经元数目
beta=10;%隐层神经元数目
lamda=3;%输出神经元数目
- 测试
%测试
[result,accuracy]=BP_test(test,test_label,W1,W2,B1,B2);
disp('结果为:')
result'
disp(strcat('准确率为',num2str(accuracy*100),'%'))
function [result,accuracy]=BP_test(test,test_label,W1,W2,B1,B2)
%返回分类的结果
%accuracy准确率
Hidden_in=test*W1;%隐层输入
Hidden_out=sigmod(Hidden_in-B1);%隐层输出
Output_in=Hidden_out*W2;%输入层输入
Output_out=sigmod(Output_in-B2);
[~,result]=max(Output_out,[],2);
[~,index2]=max(test_label,[],2);
right=sum(result==index2);%统计分类正确的个数
total=size(test,1);%总个数
accuracy=right/total;
end
%sigmod函数在matlab里是logsig函数
function [Y]=sigmod(X)
Y=1./(1+exp(-1).^X);
end
程序截图:

独立运行十次,平均准确率为95%,标准差为0.025438487。
4 决策树——ID3算法
-
计算信息熵

-
划分数据集

-
计算最大增益

程序截图:


完整代码及实验报告
Github地址:Artificial-Intelligence-Experiment-And-Homework
优快云地址:《人工智能》平时作业与实验.zip
9168

被折叠的 条评论
为什么被折叠?



