Классы ооп. Алгоритм flood fill.
Автор
Подход к реализации классов ооп. Алгоритм flood fill.¶
Под классом будем понимать mutable struct, в которую добавлены методы в качестве полей. Первый аргумент каждого метода (кроме конструктора) - это объект класса.
Класс Room.¶
In [ ]:
using Plots
mutable struct Room
width
height
plane
z
set_walls
draw
floodfill
animatedfloodfill
robot
function Room(x, y)
plane = zeros(x,y);
plane[[1, x], :] .= 1;
plane[:, [1, y]] .= 1;
function set_walls(r)
println("set_walls body")
println("width ", string(r.width))
println("height ", string(r.height))
for i in 1:(r.width / 2)
x1 = rand(1:r.width)
y1 = rand(1:r.height)
y2 = rand(1:r.height)
if y1 < y2
for j in y1:y2
r.plane[x1, j] = 1
end
end
end
for i in 1:(r.height / 2)
x1 = rand(1:r.width)
x2 = rand(1:r.width)
y1 = rand(1:r.height)
if x1 < x2
for j in x1:x2
r.plane[j, y1] = 1
end
end
end
end
function floodfill(r::Room, x, y, animated::Bool=false, A=0)
if (x < 1 || x > r.width || y < 1 || y > r.height) return; end;
if (r.plane[x, y] != 0 || r.z[x, y] != 0) return; end;
r.z[x, y] = 0.5
if animated
heatmap(RGB.(r.robot.plane, r.z, r.z) + RGB.(r.z, r.plane, r.z), cbar = :none, c = :blues)
heatmap!(title = "V1.1 Start point: " * "(" * string(r.robot.start_x) * "," * string(r.robot.start_y) * ")")
frame(A)
end
floodfill(r, x - 1, y, animated, A)
floodfill(r, x + 1, y, animated, A)
floodfill(r, x, y - 1, animated, A)
floodfill(r, x, y + 1, animated, A)
end
function draw(r::Room)
A = Animation()
heatmap(RGB.(r.robot.plane, r.z, r.z) + RGB.(r.z, r.plane, r.z), cbar = :none, c = :blues)
heatmap!(title = "V1.1 Start point: " * "(" * string(r.robot.start_x) * "," * string(r.robot.start_y) * ")")
frame(A)
gif(A, "room.gif", fps = 10)
end
function animatedfloodfill(r::Room)
A = Animation()
r.z = zeros(x, y)
r.floodfill(r, r.robot.start_x, r.robot.start_y, true, A)
gif(A, "roomA.gif", fps = 30)
end
new(x, y, plane, zeros(x, y), set_walls, draw, floodfill, animatedfloodfill)
end
end
Класс Robot.¶
In [ ]:
mutable struct Robot
start_x
start_y
plane
room
function Robot(r::Room)
x = size(r.plane,1)
y = size(r.plane,2)
gen_start_point = true
s_x = 0
s_y = 0
while gen_start_point
s_x = rand(1:x);
s_y = rand(1:y);
if r.plane[s_x, s_y] == 0
gen_start_point = false
end
end
plane = zeros(x,y);
plane[s_x, s_y] = 1
robot = new(s_x, s_y, plane, r)
r.robot = robot
end
end
Сценарий работы робота.¶
Создаем комнату:
In [ ]:
room = Room(100, 100)
room.set_walls(room)
Создаем робота в комнате:
In [ ]:
Robot(room)
println("Starting point: ", room.robot.start_x," ", room.robot.start_y)
Определяем область доступности для робота с помощью алгоритма flood fill:
In [ ]:
room.floodfill(room, room.robot.start_x, room.robot.start_y)
room.draw(room)
Out[0]:
Далее показана работа алгоритма по-шагам:
In [ ]:
room.animatedfloodfill(room)
Out[0]: