-
Notifications
You must be signed in to change notification settings - Fork 2
/
simulator.rb
77 lines (71 loc) · 2.03 KB
/
simulator.rb
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
# ----------------------------------------------------------------------------
require 'constants'
require 'storage'
require 'rules'
# ----------------------------------------------------------------------------
class Simulator
def initialize(dir, name, width, height, density)
@storage = Storage.new(dir, name, width, height)
random_life(density)
end
def snapshot
@storage.show
end
def do_step
@storage.each { |i, j, value|
neighbors = @storage.get_in_range(i, j, Rules::RANGE)
alive = 0
good = 0
viruses = []
antibodies = []
neighbors.each { |x|
case x
when CELL_GOOD_RANGE then good += 1
when CELL_VIRUS_RANGE then viruses.push x
when CELL_ANTIBODY_RANGE then antibodies.push x
else raise "Unknown cell type #{x} near (#{i},#{j})"
end
}
alive = good + viruses.size
case value
when CELL_FREE
new = Rules::new_born(alive, good, viruses, antibodies)
@storage.set!(i, j, new) if new != CELL_FREE
when CELL_GOOD_RANGE
if Rules::time_to_dead(value) or Rules::dead_from_suffocation(value, alive) then
@storage.set!(i, j, CELL_FREE)
else
res = Rules::got_virus(value, viruses, antibodies)
if res.nil? then
@storage.set!(i, j, value + 1)
else
@storage.set!(i, j, res)
end
end
when CELL_VIRUS_RANGE
if Rules::time_to_dead(value) or Rules::dead_from_suffocation(value, alive) then
@storage.set!(i, j, CELL_FREE)
else
res = Rules::virus_is_killed(value, viruses, antibodies)
if res.nil? then
@storage.set!(i, j, value + 1)
else
@storage.set!(i, j, res)
end
end
when CELL_ANTIBODY_RANGE
@storage.set!(i, j, CELL_FREE)
else raise "Unknown cell type #{value} at (#{i},#{j})"
end
}
@storage.update!
end
private
def random_life(density)
@storage.each { |i, j, value|
@storage.set!(i, j, CELL_LIFE_BORN) if rand < density
@storage.set!(i, j, CELL_LIFE_VIRUS_START) if rand < 0.02
}
end
end
# ----------------------------------------------------------------------------