本设计由matlab实现,待扩展节点放在OPEN表里,已扩展节点放在CLOSE表里,按节点f值由小到大扩展。
clear
clc
%A = [2 3 0; 7 5 6; 1 4 8];
%A = [2 5 3;7 0 6; 1 4 8];
A = [2 5 3;1 7 6; 0 4 8];
T = [1 2 3; 4 5 6; 7 8 0];
tail = 1;
OPEN=cell(1);
OPEN{
1,1}.g= 0;
OPEN{
1,1}.f= OPEN{
1,1}.g + h1(A,T);
OPEN{
1,1}.S= A; %当前节点的状态
OPEN{
1,1}.fa= 0; %父节点的index,这样的保留可以从找到的目标状态追踪到初始状态
CLOSED = [];
% result = [];
while tail>0
[OPEN,tail,CLOSED] = remove(OPEN,tail,CLOSED); % remove the smallest f
if h1(CLOSED{
1,length(CLOSED)}.S,T)==0
disp('find');
t = CLOSED{
1,length(CLOSED)}.fa;
result = CLOSED{
1,length(CLOSED)}.S;
while t>0
result = [result;CLOSED{
1,t}.S];
t = CLOSED{
1,t}.fa;
end
return
% tail
end
[OPEN,tail] = expand(OPEN,tail,CLOSED,T);
end
return
function [OPEN,tail,CLOSED] = remove(OPEN,tail,CLOSED) % find the smallest f val in open table, remove it to the closed table
min = OPEN{
1,1}.f;
index = 1;
for i=1:tail
if OPEN{
1,i}.f{
1,i}.f;
index = i;
end
end
CLOSED{
1,length(CLOSED)+1} = OPEN{
1,index};
disp(CLOSED{
1,length(CLOSED)}.S);
OPEN{
1,index} = OPEN{
1,tail};
tail = tail-1;
return
function [OPEN,tail] = expand(OPEN,tail,CLOSED,T)
node = CLOSED{
1,length(CLOSED)};
[up,down,left,right] = move8(node.S);
if check(up,OPEN,tail,CLOSED) % up is new and unduplicated
tail = tail+1;
OPEN{
1,tail}.g = node.g +1;
OPEN{
1,tail}.f = OPEN{
1,tail}.g + h1(up,T);
OPEN{
1,tail}.S = up;
OPEN{
1,tail}.fa = length(CLOSED);
end
if check(down,OPEN,tail,CLOSED) % down is new and unduplicated
tail = tail+1;
OPEN{
1,tail}.g = node.g +1;
OPEN{
1,tail}.f = OPEN{
1,tail}.g + h1(down,T);
OPEN{
1,tail}.S = down;
OPEN{
1,tail}.fa = length(CLOSED);
end
if check(left,OPEN,tail,CLOSED) % left is new and unduplicated
tail = tail+1;
OPEN{
1,tail}.g = node.g +1;
OPEN{
1,tail}.f = OPEN{
1,tail}.g + h1(left,T);
OPEN{
1,tail}.S = left;
OPEN{
1,tail}.fa = length(CLOSED);
end
if check(right,OPEN,tail,CLOSED) % right is new and unduplicated
tail = tail+1;
OPEN{
1,tail}.g = node.g +1;
OPEN{
1,tail}.f = OPEN{
1,tail}.g + h1(right,T);
OPEN{
1,tail}.S = right;
OPEN{
1,tail}.fa = length(CLOSED);
end
return
function [U,D,L,R]=move8(A)
U=A;
D=A;
L=A;
R=A;
[x,y]=find(A==0);
if (x~=1)
t=U(x,y);
U(x,y)=U(x-1,y);
U(x-1,y)=t;
else
U=-1;
end
if (x~=3)
t=D(x,y);
D(x,y)=D(x+1,y);
D(x+1,y)=t;
else
D=-1;
end
if (y~=1)
t=L(x,y);
L(x,y)=L(x,y-1);
L(x,y-1)=t;
else
L=-1;
end
if (y~=3)
t=R(x,y);
R(x,y)=R(x,y+1);
R(x,y+1)=t;
else
R=-1;
end
end
function val=h1(A,T)
val=0;
B=A-T;
index=find(B~=0);
val=length(index);
function a=check(temp,OPEN,tail,CLOSED)
a=1;
if temp==-1
a=0;
return
end
for i=1:tail
if temp==OPEN{
1,i}.S
a=0;
return
end
end
for i=1:length(CLOSED)
if temp==CLOSED{
1,i}.S
a=0;
return
end
end
return