目前大多数细胞自动机都是矩形的,这个是六边形的。
生存规则在倒数13 - 倒数18行。
下面是两种不同规则的动画。
clear;
N_col = 20;
% 列数设置
N_row = round(N_col/0.433*1.5/1.2);
Cell = zeros(N_row,N_col, 14,2);
% Cell - [细胞状态 细胞中点坐标 六个边点坐标 六个邻近图形序号]
% 细胞状态(1)- [当前状态 下一步状态]; 0- 死亡 ,1- 存活。
% 中方点坐标(2)- [x, y]
% 六个边点坐标(3~8)- [x,y]。
% 六个邻近图形行、列号(9~14)- [行号,列号]。
% 生成六边形中点坐标 %
y_point= 0;
for i_row =1:1:N_row
if(mod(i_row,2)==1)
x_point = 0.5;
else
x_point = 1.25;
end
y_point= y_point+ 0.433;
for i_col = 1:1:N_col
x_point = x_point+ 1.5;
Cell(i_row, i_col,2,:)= [x_point,y_point];
end
end
% 生成六边形角点坐标 %
Cell(:,:,3,1)= Cell(:,: ,2,1)-0.5;
Cell(:,:,[4,8],1)= repmat(Cell(:,: ,2,1)-0.25,1,1,2);
Cell(:,:,[5,7],1)= repmat(Cell(:,: ,2,1)+0.25,1,1,2);
Cell(:,:,6,1)= Cell(:,: ,2,1)+0.5;
Cell(:,:,[3,6],2)= repmat(Cell(:,: ,2,2),1,1,2);
Cell(:,:,[4,5],2)= repmat(Cell(:,: ,2,2)+0.433,1,1,2);
Cell(:,:,[7,8],2)= repmat(Cell(:,: ,2,2)-0.433,1,1,2);
% 绘制中点 %
plot(Cell(:, :,2,1),Cell(:, :,2,2),'LineStyle','none','Marker','.','color','b' );hold on;
if(Cell(N_row,N_col,2,1)>1.2*Cell(N_row,N_col,2,2))
xlim([0, Cell(N_row,N_col,2,1)]+1.5);ylim([0, Cell(N_row,N_col,2,1)]./1.2);
else
xlim([0, Cell(N_row,N_col,2,2).*1.2+1]);ylim([0, Cell(N_row,N_col,2,2)]);
end
% 绘制六边形 %
pic= cell(N_row,N_col);
for i=1:1:N_row
for j=1:1:N_col
pic{i,j}= patch(reshape(Cell(i,j,3:8,1),[1,6]),reshape(Cell(i,j,3:8,2),[1,6]),'w');
end
end
% 寻找邻近图形的行、列号(没有细胞的位置为[-1,-1])
for i_center=1:1:N_row
for j_center=1:1:N_col
for i=1:1:6
found = 0;
% 在目标细胞附近 士2 格的范围内寻找,减少运算量
for i_find= max(1, i_center-2):min(N_row, i_center+2)
for j_find= max(1, j_center-2):min(N_col, j_center+2)
distance = sqrt((Cell(i_center, j_center,2,1)- Cell(i_find, j_find,2,1))^2 ...
+ (Cell(i_center, j_center,2,2)- Cell(i_find, j_find,2,2))^2);
% 初步根据距离判断
if distance> 0.85 && distance< 0.9
x_range = [1,1].* cos(1.0472* (i-1)-0.5236)* distance+ [-0.1 0.1]+ Cell(i_center, j_center,2,1);
y_range = [1,1].* sin(1.0472* (i-1)-0.5236)* distance+ [-0.1 0.1]+ Cell(i_center, j_center,2,2);
% 再根据夹角判断
if Cell(i_find, j_find,2,1)> x_range(1) && Cell(i_find, j_find,2,1)< x_range(2) ...
&& Cell(i_find, j_find,2,2)> y_range(1) && Cell(i_find, j_find,2,2)< y_range(2)
Cell(i_center, j_center,i+8,:) = [i_find, j_find];
found= 1;
end
end
end
end
if found ==0
Cell(i_center, j_center,i+8,:)= -1;
end
end
end
end
% 赋予细胞随机初试状态
Cell( :, :, 1, 1)=round(rand(N_row, N_col));
% 开始迭代
while 2>1
for i=1:1:N_row
for j=1:1:N_col
% 计算细胞周围存活细胞数量
N_live = 0;
for k=1:1:6
if Cell( i, j, k+8, 1)~= -1 && Cell( i, j, k+8, 2)~= -1
N_live = N_live+ Cell(Cell( i, j, k+8, 1), Cell( i, j, k+8, 2), 1, 1);
end
end
% 判断生死
if N_live>4 || N_live<3
Cell( i, j, 1, 2)= 0;
else
Cell( i, j, 1, 2)= 1;
end
% 更新显示状态
if Cell( i, j, 1, 1) >0.5
set(pic{i, j},'FaceColor',[0.5 1 0.5]);
else
set(pic{i, j},'FaceColor',[1 1 1]);
end
end
end
drawnow;
% 更新生死状态
Cell( :, :, 1, 1)= Cell( :, :, 1, 2);
end