Some work on flow, but mainly tidyup.

This commit is contained in:
Simon Brooke 2023-07-11 08:22:54 +01:00
parent 4f35557b38
commit 866c00bea0
37 changed files with 5840 additions and 623 deletions

View file

@ -0,0 +1,40 @@
.covered {
font-family: 'Bitstream Vera Sans Mono', 'Courier', monospace;
background-color: #558B55;
}
.not-covered {
font-family: 'Bitstream Vera Sans Mono', 'Courier', monospace;
background-color: red;
}
.partial {
font-family: 'Bitstream Vera Sans Mono', 'Courier', monospace;
background-color: orange;
}
.not-tracked {
font-family: 'Bitstream Vera Sans Mono', 'Courier', monospace;
}
.blank {
font-family: 'Bitstream Vera Sans Mono', 'Courier', monospace;
}
td {
padding-right: 10px;
}
td.with-bar {
width: 250px;
text-align: center;
}
td.with-number {
text-align: right;
}
td.ns-name {
min-width: 150px;
padding-right: 25px;
}

157
docs/cloverage/index.html Normal file
View file

@ -0,0 +1,157 @@
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<link rel="stylesheet" href="./coverage.css"/>
<title>Coverage Summary</title>
</head>
<body>
<table>
<thead><tr>
<td class="ns-name"> Namespace </td>
<td class="with-bar"> Forms </td>
<td class="with-number">Forms %</td>
<td class="with-bar"> Lines </td>
<td class="with-number">Lines %</td>
<td class="with-number">Total</td><td class="with-number">Blank</td><td class="with-number">Instrumented</td>
</tr></thead>
<tr>
<td><a href="mw_engine/core.clj.html">mw-engine.core</a></td><td class="with-bar"><div class="covered"
style="width:33.116883116883116%;
float:left;"> 51 </div><div class="not-covered"
style="width:66.88311688311688%;
float:left;"> 103 </div></td>
<td class="with-number">33.12 %</td>
<td class="with-bar"><div class="covered"
style="width:36.36363636363637%;
float:left;"> 12 </div><div class="partial"
style="width:3.0303030303030303%;
float:left;"> 1 </div><div class="not-covered"
style="width:60.60606060606061%;
float:left;"> 20 </div></td>
<td class="with-number">39.39 %</td>
<td class="with-number">115</td><td class="with-number">15</td><td class="with-number">33</td>
</tr>
<tr>
<td><a href="mw_engine/display.clj.html">mw-engine.display</a></td><td class="with-bar"><div class="covered"
style="width:10.227272727272727%;
float:left;"> 9 </div><div class="not-covered"
style="width:89.77272727272727%;
float:left;"> 79 </div></td>
<td class="with-number">10.23 %</td>
<td class="with-bar"><div class="covered"
style="width:42.10526315789474%;
float:left;"> 8 </div><div class="not-covered"
style="width:57.89473684210526%;
float:left;"> 11 </div></td>
<td class="with-number">42.11 %</td>
<td class="with-number">65</td><td class="with-number">8</td><td class="with-number">19</td>
</tr>
<tr>
<td><a href="mw_engine/drainage.clj.html">mw-engine.drainage</a></td><td class="with-bar"><div class="covered"
style="width:22.62210796915167%;
float:left;"> 88 </div><div class="not-covered"
style="width:77.37789203084833%;
float:left;"> 301 </div></td>
<td class="with-number">22.62 %</td>
<td class="with-bar"><div class="covered"
style="width:34.44444444444444%;
float:left;"> 31 </div><div class="not-covered"
style="width:65.55555555555556%;
float:left;"> 59 </div></td>
<td class="with-number">34.44 %</td>
<td class="with-number">217</td><td class="with-number">30</td><td class="with-number">90</td>
</tr>
<tr>
<td><a href="mw_engine/flow.clj.html">mw-engine.flow</a></td><td class="with-bar"><div class="covered"
style="width:86.62790697674419%;
float:left;"> 447 </div><div class="not-covered"
style="width:13.372093023255815%;
float:left;"> 69 </div></td>
<td class="with-number">86.63 %</td>
<td class="with-bar"><div class="covered"
style="width:85.45454545454545%;
float:left;"> 47 </div><div class="partial"
style="width:7.2727272727272725%;
float:left;"> 4 </div><div class="not-covered"
style="width:7.2727272727272725%;
float:left;"> 4 </div></td>
<td class="with-number">92.73 %</td>
<td class="with-number">141</td><td class="with-number">15</td><td class="with-number">55</td>
</tr>
<tr>
<td><a href="mw_engine/heightmap.clj.html">mw-engine.heightmap</a></td><td class="with-bar"><div class="covered"
style="width:92.51700680272108%;
float:left;"> 136 </div><div class="not-covered"
style="width:7.482993197278912%;
float:left;"> 11 </div></td>
<td class="with-number">92.52 %</td>
<td class="with-bar"><div class="covered"
style="width:90.9090909090909%;
float:left;"> 40 </div><div class="partial"
style="width:4.545454545454546%;
float:left;"> 2 </div><div class="not-covered"
style="width:4.545454545454546%;
float:left;"> 2 </div></td>
<td class="with-number">95.45 %</td>
<td class="with-number">127</td><td class="with-number">11</td><td class="with-number">44</td>
</tr>
<tr>
<td><a href="mw_engine/natural_rules.clj.html">mw-engine.natural-rules</a></td><td class="with-bar"><div class="covered"
style="width:7.774390243902439%;
float:left;"> 51 </div><div class="not-covered"
style="width:92.22560975609755%;
float:left;"> 605 </div></td>
<td class="with-number">7.77 %</td>
<td class="with-bar"><div class="covered"
style="width:33.0188679245283%;
float:left;"> 35 </div><div class="partial"
style="width:4.716981132075472%;
float:left;"> 5 </div><div class="not-covered"
style="width:62.264150943396224%;
float:left;"> 66 </div></td>
<td class="with-number">37.74 %</td>
<td class="with-number">184</td><td class="with-number">14</td><td class="with-number">106</td>
</tr>
<tr>
<td><a href="mw_engine/utils.clj.html">mw-engine.utils</a></td><td class="with-bar"><div class="covered"
style="width:69.88847583643123%;
float:left;"> 376 </div><div class="not-covered"
style="width:30.111524163568774%;
float:left;"> 162 </div></td>
<td class="with-number">69.89 %</td>
<td class="with-bar"><div class="covered"
style="width:73.21428571428571%;
float:left;"> 82 </div><div class="partial"
style="width:0.8928571428571429%;
float:left;"> 1 </div><div class="not-covered"
style="width:25.892857142857142%;
float:left;"> 29 </div></td>
<td class="with-number">74.11 %</td>
<td class="with-number">301</td><td class="with-number">35</td><td class="with-number">112</td>
</tr>
<tr>
<td><a href="mw_engine/world.clj.html">mw-engine.world</a></td><td class="with-bar"><div class="covered"
style="width:54.310344827586206%;
float:left;"> 63 </div><div class="not-covered"
style="width:45.689655172413794%;
float:left;"> 53 </div></td>
<td class="with-number">54.31 %</td>
<td class="with-bar"><div class="covered"
style="width:42.30769230769231%;
float:left;"> 11 </div><div class="partial"
style="width:3.8461538461538463%;
float:left;"> 1 </div><div class="not-covered"
style="width:53.84615384615385%;
float:left;"> 14 </div></td>
<td class="with-number">46.15 %</td>
<td class="with-number">89</td><td class="with-number">12</td><td class="with-number">26</td>
</tr>
<tr><td>Totals:</td>
<td class="with-bar"></td>
<td class="with-number">46.89 %</td>
<td class="with-bar"></td>
<td class="with-number">57.73 %</td>
</tr>
</table>
</body>
</html>

View file

@ -0,0 +1,353 @@
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<link rel="stylesheet" href="../coverage.css"/> <title> mw_engine/core.clj </title>
</head>
<body>
<span class="covered" title="1 out of 1 forms covered">
001&nbsp;&nbsp;(ns&nbsp;^{:doc&nbsp;&quot;Functions&nbsp;to&nbsp;transform&nbsp;a&nbsp;world&nbsp;and&nbsp;run&nbsp;rules.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
002&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
003&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Every&nbsp;rule&nbsp;is&nbsp;a&nbsp;function&nbsp;of&nbsp;two&nbsp;arguments,&nbsp;a&nbsp;cell&nbsp;and&nbsp;a&nbsp;world.&nbsp;If&nbsp;the&nbsp;rule
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
004&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;fires,&nbsp;it&nbsp;returns&nbsp;a&nbsp;new&nbsp;cell,&nbsp;which&nbsp;should&nbsp;have&nbsp;the&nbsp;same&nbsp;values&nbsp;for&nbsp;`:x`&nbsp;and
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
005&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;`:y`&nbsp;as&nbsp;the&nbsp;old&nbsp;cell.&nbsp;Anything&nbsp;else&nbsp;can&nbsp;be&nbsp;modified.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
006&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
007&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;While&nbsp;any&nbsp;function&nbsp;of&nbsp;two&nbsp;arguments&nbsp;can&nbsp;be&nbsp;used&nbsp;as&nbsp;a&nbsp;rule,&nbsp;a&nbsp;special&nbsp;high
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
008&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;level&nbsp;rule&nbsp;language&nbsp;is&nbsp;provided&nbsp;by&nbsp;the&nbsp;`mw-parser`&nbsp;package,&nbsp;which&nbsp;compiles
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
009&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;rules&nbsp;expressed&nbsp;in&nbsp;a&nbsp;subset&nbsp;of&nbsp;English&nbsp;rules&nbsp;into&nbsp;suitable&nbsp;functions.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
010&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
011&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;A&nbsp;cell&nbsp;is&nbsp;a&nbsp;map&nbsp;containing&nbsp;at&nbsp;least&nbsp;values&nbsp;for&nbsp;the&nbsp;keys&nbsp;:x,&nbsp;:y,&nbsp;and&nbsp;:state;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
012&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;a&nbsp;transformation&nbsp;should&nbsp;not&nbsp;alter&nbsp;the&nbsp;values&nbsp;of&nbsp;:x&nbsp;or&nbsp;:y,&nbsp;and&nbsp;should&nbsp;not
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
013&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return&nbsp;a&nbsp;cell&nbsp;without&nbsp;a&nbsp;keyword&nbsp;as&nbsp;the&nbsp;value&nbsp;of&nbsp;:state.&nbsp;Anything&nbsp;else&nbsp;is
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
014&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;legal.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
015&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
016&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;A&nbsp;world&nbsp;is&nbsp;a&nbsp;two&nbsp;dimensional&nbsp;matrix&nbsp;(sequence&nbsp;of&nbsp;sequences)&nbsp;of&nbsp;cells,&nbsp;such
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
017&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;that&nbsp;every&nbsp;cell&#x27;s&nbsp;`:x`&nbsp;and&nbsp;`:y`&nbsp;properties&nbsp;reflect&nbsp;its&nbsp;place&nbsp;in&nbsp;the&nbsp;matrix.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
018&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;See&nbsp;`world.clj`.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
019&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
020&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Each&nbsp;time&nbsp;the&nbsp;world&nbsp;is&nbsp;transformed&nbsp;(see&nbsp;`transform-world`),&nbsp;for&nbsp;each&nbsp;cell,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
021&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;rules&nbsp;are&nbsp;applied&nbsp;in&nbsp;turn&nbsp;until&nbsp;one&nbsp;matches.&nbsp;Once&nbsp;one&nbsp;rule&nbsp;has&nbsp;matched&nbsp;no
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
022&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;further&nbsp;rules&nbsp;can&nbsp;be&nbsp;applied&nbsp;to&nbsp;that&nbsp;cell.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
023&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:author&nbsp;&quot;Simon&nbsp;Brooke&quot;}
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
024&nbsp;&nbsp;&nbsp;mw-engine.core
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
025&nbsp;&nbsp;&nbsp;&nbsp;(:require&nbsp;[mw-engine.utils&nbsp;:refer&nbsp;[get-int-or-zero&nbsp;map-world]]
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
026&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[taoensso.timbre&nbsp;:as&nbsp;l]))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
027&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
028&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
029&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
030&nbsp;&nbsp;;;;;&nbsp;mw-engine:&nbsp;the&nbsp;state&#x2F;transition&nbsp;engine&nbsp;of&nbsp;MicroWorld.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
031&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
032&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;free&nbsp;software;&nbsp;you&nbsp;can&nbsp;redistribute&nbsp;it&nbsp;and&#x2F;or
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
033&nbsp;&nbsp;;;;;&nbsp;modify&nbsp;it&nbsp;under&nbsp;the&nbsp;terms&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
034&nbsp;&nbsp;;;;;&nbsp;as&nbsp;published&nbsp;by&nbsp;the&nbsp;Free&nbsp;Software&nbsp;Foundation;&nbsp;either&nbsp;version&nbsp;2
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
035&nbsp;&nbsp;;;;;&nbsp;of&nbsp;the&nbsp;License,&nbsp;or&nbsp;(at&nbsp;your&nbsp;option)&nbsp;any&nbsp;later&nbsp;version.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
036&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
037&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;distributed&nbsp;in&nbsp;the&nbsp;hope&nbsp;that&nbsp;it&nbsp;will&nbsp;be&nbsp;useful,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
038&nbsp;&nbsp;;;;;&nbsp;but&nbsp;WITHOUT&nbsp;ANY&nbsp;WARRANTY;&nbsp;without&nbsp;even&nbsp;the&nbsp;implied&nbsp;warranty&nbsp;of
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
039&nbsp;&nbsp;;;;;&nbsp;MERCHANTABILITY&nbsp;or&nbsp;FITNESS&nbsp;FOR&nbsp;A&nbsp;PARTICULAR&nbsp;PURPOSE.&nbsp;&nbsp;See&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
040&nbsp;&nbsp;;;;;&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License&nbsp;for&nbsp;more&nbsp;details.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
041&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
042&nbsp;&nbsp;;;;;&nbsp;You&nbsp;should&nbsp;have&nbsp;received&nbsp;a&nbsp;copy&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
043&nbsp;&nbsp;;;;;&nbsp;along&nbsp;with&nbsp;this&nbsp;program;&nbsp;if&nbsp;not,&nbsp;write&nbsp;to&nbsp;the&nbsp;Free&nbsp;Software
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
044&nbsp;&nbsp;;;;;&nbsp;Foundation,&nbsp;Inc.,&nbsp;51&nbsp;Franklin&nbsp;Street,&nbsp;Fifth&nbsp;Floor,&nbsp;Boston,&nbsp;MA&nbsp;&nbsp;02110-1301,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
045&nbsp;&nbsp;;;;;&nbsp;USA.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
046&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
047&nbsp;&nbsp;;;;;&nbsp;Copyright&nbsp;(C)&nbsp;2014&nbsp;Simon&nbsp;Brooke
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
048&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
049&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
050&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
051&nbsp;&nbsp;(defn&nbsp;apply-rule
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
052&nbsp;&nbsp;&nbsp;&nbsp;&quot;Apply&nbsp;a&nbsp;single&nbsp;`rule`&nbsp;to&nbsp;a&nbsp;`cell`.&nbsp;What&nbsp;this&nbsp;is&nbsp;about&nbsp;is&nbsp;that&nbsp;I&nbsp;want&nbsp;to&nbsp;be&nbsp;able,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
053&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;for&nbsp;debugging&nbsp;purposes,&nbsp;to&nbsp;tag&nbsp;a&nbsp;cell&nbsp;with&nbsp;the&nbsp;rule&nbsp;text&nbsp;of&nbsp;the&nbsp;rule&nbsp;which
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
054&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;fired&nbsp;(and&nbsp;especially&nbsp;so&nbsp;when&nbsp;an&nbsp;exception&nbsp;is&nbsp;thrown.&nbsp;So&nbsp;a&nbsp;rule&nbsp;may&nbsp;be&nbsp;either
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
055&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;an&nbsp;ifn,&nbsp;or&nbsp;a&nbsp;list&nbsp;(ifn&nbsp;source-text).&nbsp;This&nbsp;function&nbsp;deals&nbsp;with&nbsp;despatching
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
056&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;on&nbsp;those&nbsp;two&nbsp;possibilities.&nbsp;`world`&nbsp;is&nbsp;also&nbsp;passed&nbsp;in&nbsp;in&nbsp;order&nbsp;to&nbsp;be&nbsp;able
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
057&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;to&nbsp;access&nbsp;neighbours.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
058&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;cell&nbsp;rule]
</span><br/>
<span class="partial" title="2 out of 3 forms covered">
059&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond
</span><br/>
<span class="covered" title="9 out of 9 forms covered">
060&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(ifn?&nbsp;rule)&nbsp;(apply-rule&nbsp;world&nbsp;cell&nbsp;rule&nbsp;nil)
</span><br/>
<span class="covered" title="11 out of 11 forms covered">
061&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(seq?&nbsp;rule)&nbsp;(let&nbsp;[[afn&nbsp;src]&nbsp;rule]&nbsp;(apply-rule&nbsp;world&nbsp;cell&nbsp;afn&nbsp;src))))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
062&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;cell&nbsp;rule&nbsp;source]
</span><br/>
<span class="covered" title="8 out of 8 forms covered">
063&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[result&nbsp;(apply&nbsp;rule&nbsp;(list&nbsp;cell&nbsp;world))]
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
064&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond
</span><br/>
<span class="covered" title="12 out of 12 forms covered">
065&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(and&nbsp;result&nbsp;source)&nbsp;(merge&nbsp;result&nbsp;{:rule&nbsp;source})
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
066&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:else&nbsp;result))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
067&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
068&nbsp;&nbsp;(defn-&nbsp;apply-rules
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
069&nbsp;&nbsp;&nbsp;&nbsp;&quot;Derive&nbsp;a&nbsp;cell&nbsp;from&nbsp;this&nbsp;`cell`&nbsp;of&nbsp;this&nbsp;`world`&nbsp;by&nbsp;applying&nbsp;these&nbsp;`rules`.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
070&nbsp;&nbsp;&nbsp;&nbsp;[world&nbsp;cell&nbsp;rules]
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
071&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(empty?&nbsp;rules)&nbsp;cell
</span><br/>
<span class="not-covered" title="0 out of 8 forms covered">
072&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:else&nbsp;(let&nbsp;[result&nbsp;(apply-rule&nbsp;world&nbsp;cell&nbsp;(first&nbsp;rules))]
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
073&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;result&nbsp;result
</span><br/>
<span class="not-covered" title="0 out of 7 forms covered">
074&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:else&nbsp;(apply-rules&nbsp;world&nbsp;cell&nbsp;(rest&nbsp;rules))))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
075&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
076&nbsp;&nbsp;(defn-&nbsp;transform-cell
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
077&nbsp;&nbsp;&nbsp;&nbsp;&quot;Derive&nbsp;a&nbsp;cell&nbsp;from&nbsp;this&nbsp;`cell`&nbsp;of&nbsp;this&nbsp;`world`&nbsp;by&nbsp;applying&nbsp;these&nbsp;`rules`.&nbsp;If&nbsp;an
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
078&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;exception&nbsp;is&nbsp;thrown,&nbsp;cache&nbsp;its&nbsp;message&nbsp;on&nbsp;the&nbsp;cell&nbsp;and&nbsp;set&nbsp;it&#x27;s&nbsp;state&nbsp;to&nbsp;error&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
079&nbsp;&nbsp;&nbsp;&nbsp;[world&nbsp;cell&nbsp;rules]
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
080&nbsp;&nbsp;&nbsp;&nbsp;(try
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
081&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
082&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(apply-rules&nbsp;world&nbsp;cell&nbsp;rules)
</span><br/>
<span class="not-covered" title="0 out of 8 forms covered">
083&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{:generation&nbsp;(+&nbsp;(get-int-or-zero&nbsp;cell&nbsp;:generation)&nbsp;1)})
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
084&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(catch&nbsp;Exception&nbsp;e
</span><br/>
<span class="not-covered" title="0 out of 8 forms covered">
085&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:error
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
086&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(format&nbsp;&quot;%s&nbsp;at&nbsp;generation&nbsp;%d&nbsp;when&nbsp;in&nbsp;state&nbsp;%s&quot;
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
087&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(.getMessage&nbsp;e)
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
088&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(:generation&nbsp;cell)
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
089&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(:state&nbsp;cell))
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
090&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:stacktrace&nbsp;(map&nbsp;#(.toString&nbsp;%)&nbsp;(.getStackTrace&nbsp;e))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
091&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:state&nbsp;:error}))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
092&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
093&nbsp;&nbsp;(defn&nbsp;transform-world
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
094&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;a&nbsp;world&nbsp;derived&nbsp;from&nbsp;this&nbsp;`world`&nbsp;by&nbsp;applying&nbsp;these&nbsp;`rules`&nbsp;to&nbsp;each&nbsp;cell.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
095&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;rules]
</span><br/>
<span class="not-covered" title="0 out of 7 forms covered">
096&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map-world&nbsp;world&nbsp;transform-cell&nbsp;(list&nbsp;rules))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
097&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
098&nbsp;&nbsp;(defn&nbsp;run-world
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
099&nbsp;&nbsp;&nbsp;&nbsp;&quot;Run&nbsp;this&nbsp;world&nbsp;with&nbsp;these&nbsp;rules&nbsp;for&nbsp;this&nbsp;number&nbsp;of&nbsp;generations.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
100&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
101&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;a&nbsp;world&nbsp;as&nbsp;discussed&nbsp;above;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
102&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`init-rules`&nbsp;a&nbsp;sequence&nbsp;of&nbsp;rules&nbsp;as&nbsp;defined&nbsp;above,&nbsp;to&nbsp;be&nbsp;run&nbsp;once&nbsp;to&nbsp;initialise&nbsp;the&nbsp;world;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
103&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`rules`&nbsp;a&nbsp;sequence&nbsp;of&nbsp;rules&nbsp;as&nbsp;defined&nbsp;above,&nbsp;to&nbsp;be&nbsp;run&nbsp;iteratively&nbsp;for&nbsp;each&nbsp;generation;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
104&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`generations`&nbsp;an&nbsp;(integer)&nbsp;number&nbsp;of&nbsp;generations.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
105&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
106&nbsp;&nbsp;&nbsp;&nbsp;Return&nbsp;the&nbsp;final&nbsp;generation&nbsp;of&nbsp;the&nbsp;world.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
107&nbsp;&nbsp;&nbsp;&nbsp;[world&nbsp;init-rules&nbsp;rules&nbsp;generations]
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
108&nbsp;&nbsp;&nbsp;&nbsp;(reduce&nbsp;(fn&nbsp;[world&nbsp;iteration]
</span><br/>
<span class="not-covered" title="0 out of 17 forms covered">
109&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(l&#x2F;info&nbsp;&quot;Running&nbsp;iteration&nbsp;&quot;&nbsp;iteration)
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
110&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(transform-world&nbsp;world&nbsp;rules))
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
111&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(transform-world&nbsp;world&nbsp;init-rules)
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
112&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(range&nbsp;generations)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
113&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
114&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
115&nbsp;&nbsp;
</span><br/>
</body>
</html>

View file

@ -0,0 +1,203 @@
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<link rel="stylesheet" href="../coverage.css"/> <title> mw_engine/display.clj </title>
</head>
<body>
<span class="covered" title="1 out of 1 forms covered">
001&nbsp;&nbsp;(ns&nbsp;^{:doc&nbsp;&quot;Simple&nbsp;functions&nbsp;to&nbsp;allow&nbsp;a&nbsp;world&nbsp;to&nbsp;be&nbsp;visualised.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
002&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:author&nbsp;&quot;Simon&nbsp;Brooke&quot;}
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
003&nbsp;&nbsp;&nbsp;&nbsp;mw-engine.display)
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
004&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
005&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
006&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
007&nbsp;&nbsp;;;;;&nbsp;mw-engine:&nbsp;the&nbsp;state&#x2F;transition&nbsp;engine&nbsp;of&nbsp;MicroWorld.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
008&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
009&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;free&nbsp;software;&nbsp;you&nbsp;can&nbsp;redistribute&nbsp;it&nbsp;and&#x2F;or
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
010&nbsp;&nbsp;;;;;&nbsp;modify&nbsp;it&nbsp;under&nbsp;the&nbsp;terms&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
011&nbsp;&nbsp;;;;;&nbsp;as&nbsp;published&nbsp;by&nbsp;the&nbsp;Free&nbsp;Software&nbsp;Foundation;&nbsp;either&nbsp;version&nbsp;2
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
012&nbsp;&nbsp;;;;;&nbsp;of&nbsp;the&nbsp;License,&nbsp;or&nbsp;(at&nbsp;your&nbsp;option)&nbsp;any&nbsp;later&nbsp;version.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
013&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
014&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;distributed&nbsp;in&nbsp;the&nbsp;hope&nbsp;that&nbsp;it&nbsp;will&nbsp;be&nbsp;useful,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
015&nbsp;&nbsp;;;;;&nbsp;but&nbsp;WITHOUT&nbsp;ANY&nbsp;WARRANTY;&nbsp;without&nbsp;even&nbsp;the&nbsp;implied&nbsp;warranty&nbsp;of
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
016&nbsp;&nbsp;;;;;&nbsp;MERCHANTABILITY&nbsp;or&nbsp;FITNESS&nbsp;FOR&nbsp;A&nbsp;PARTICULAR&nbsp;PURPOSE.&nbsp;&nbsp;See&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
017&nbsp;&nbsp;;;;;&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License&nbsp;for&nbsp;more&nbsp;details.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
018&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
019&nbsp;&nbsp;;;;;&nbsp;You&nbsp;should&nbsp;have&nbsp;received&nbsp;a&nbsp;copy&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
020&nbsp;&nbsp;;;;;&nbsp;along&nbsp;with&nbsp;this&nbsp;program;&nbsp;if&nbsp;not,&nbsp;write&nbsp;to&nbsp;the&nbsp;Free&nbsp;Software
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
021&nbsp;&nbsp;;;;;&nbsp;Foundation,&nbsp;Inc.,&nbsp;51&nbsp;Franklin&nbsp;Street,&nbsp;Fifth&nbsp;Floor,&nbsp;Boston,&nbsp;MA&nbsp;&nbsp;02110-1301,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
022&nbsp;&nbsp;;;;;&nbsp;USA.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
023&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
024&nbsp;&nbsp;;;;;&nbsp;Copyright&nbsp;(C)&nbsp;2014&nbsp;Simon&nbsp;Brooke
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
025&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
026&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
027&nbsp;&nbsp;
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
028&nbsp;&nbsp;(def&nbsp;^:dynamic&nbsp;*image-base*
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
029&nbsp;&nbsp;&nbsp;&nbsp;&quot;Base&nbsp;url&nbsp;(i.e.,&nbsp;url&nbsp;of&nbsp;directory)&nbsp;from&nbsp;which&nbsp;to&nbsp;load&nbsp;tile&nbsp;images.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
030&nbsp;&nbsp;&nbsp;&nbsp;&quot;img&#x2F;tiles&quot;)
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
031&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
032&nbsp;&nbsp;(defn&nbsp;format-css-class
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
033&nbsp;&nbsp;&nbsp;&nbsp;&quot;Format&nbsp;this&nbsp;`state`,&nbsp;assumed&nbsp;to&nbsp;be&nbsp;a&nbsp;keyword&nbsp;indicating&nbsp;a&nbsp;state&nbsp;in&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
034&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;world,&nbsp;into&nbsp;a&nbsp;CSS&nbsp;class&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
035&nbsp;&nbsp;&nbsp;&nbsp;[state]
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
036&nbsp;&nbsp;&nbsp;&nbsp;(subs&nbsp;(str&nbsp;state)&nbsp;1))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
037&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
038&nbsp;&nbsp;(defn&nbsp;format-image-path
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
039&nbsp;&nbsp;&nbsp;&nbsp;&quot;Render&nbsp;this&nbsp;`state`,&nbsp;assumed&nbsp;to&nbsp;be&nbsp;a&nbsp;keyword&nbsp;indicating&nbsp;a&nbsp;state&nbsp;in&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
040&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;world,&nbsp;into&nbsp;a&nbsp;path&nbsp;which&nbsp;should&nbsp;recover&nbsp;the&nbsp;corresponding&nbsp;image&nbsp;file.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
041&nbsp;&nbsp;&nbsp;&nbsp;[state]
</span><br/>
<span class="not-covered" title="0 out of 7 forms covered">
042&nbsp;&nbsp;&nbsp;&nbsp;(format&nbsp;&quot;%s&#x2F;%s.png&quot;&nbsp;*image-base*&nbsp;(format-css-class&nbsp;state)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
043&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
044&nbsp;&nbsp;(defn&nbsp;format-mouseover&nbsp;[cell]
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
045&nbsp;&nbsp;&nbsp;&nbsp;(str&nbsp;cell))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
046&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
047&nbsp;&nbsp;(defn&nbsp;render-cell
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
048&nbsp;&nbsp;&nbsp;&nbsp;&quot;Render&nbsp;this&nbsp;world&nbsp;cell&nbsp;as&nbsp;a&nbsp;Hiccup&nbsp;table&nbsp;cell.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
049&nbsp;&nbsp;&nbsp;&nbsp;[cell]
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
050&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[state&nbsp;(:state&nbsp;cell)]
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
051&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[:td&nbsp;{:class&nbsp;(format-css-class&nbsp;state)&nbsp;:title&nbsp;(format-mouseover&nbsp;cell)}
</span><br/>
<span class="not-covered" title="0 out of 13 forms covered">
052&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[:a&nbsp;{:href&nbsp;(format&nbsp;&quot;inspect?x=%d&amp;y=%d&quot;&nbsp;(:x&nbsp;cell)&nbsp;(:y&nbsp;cell))}
</span><br/>
<span class="not-covered" title="0 out of 15 forms covered">
053&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[:img&nbsp;{:alt&nbsp;(:state&nbsp;cell)&nbsp;:width&nbsp;32&nbsp;:height&nbsp;32&nbsp;:src&nbsp;(format-image-path&nbsp;state)}]]]))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
054&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
055&nbsp;&nbsp;(defn&nbsp;render-world-row
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
056&nbsp;&nbsp;&nbsp;&nbsp;&quot;Render&nbsp;this&nbsp;world&nbsp;`row`&nbsp;as&nbsp;a&nbsp;Hiccup&nbsp;table&nbsp;row.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
057&nbsp;&nbsp;&nbsp;&nbsp;[row]
</span><br/>
<span class="not-covered" title="0 out of 10 forms covered">
058&nbsp;&nbsp;&nbsp;&nbsp;(apply&nbsp;vector&nbsp;(cons&nbsp;:tr&nbsp;(map&nbsp;render-cell&nbsp;row))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
059&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
060&nbsp;&nbsp;(defn&nbsp;render-world-table
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
061&nbsp;&nbsp;&nbsp;&nbsp;&quot;Render&nbsp;this&nbsp;`world`&nbsp;as&nbsp;a&nbsp;Hiccup&nbsp;table.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
062&nbsp;&nbsp;&nbsp;&nbsp;[world]
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
063&nbsp;&nbsp;&nbsp;&nbsp;(apply&nbsp;vector
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
064&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cons&nbsp;:table
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
065&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map&nbsp;render-world-row&nbsp;world))))
</span><br/>
</body>
</html>

View file

@ -0,0 +1,659 @@
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<link rel="stylesheet" href="../coverage.css"/> <title> mw_engine/drainage.clj </title>
</head>
<body>
<span class="covered" title="1 out of 1 forms covered">
001&nbsp;&nbsp;(ns&nbsp;^{:doc&nbsp;&quot;Experimental,&nbsp;probably&nbsp;of&nbsp;no&nbsp;interest&nbsp;to&nbsp;anyone&nbsp;else;&nbsp;attempt&nbsp;to
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
002&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;compute&nbsp;drainage&nbsp;on&nbsp;a&nbsp;world,&nbsp;assumed&nbsp;to&nbsp;have&nbsp;altitudes&nbsp;already&nbsp;set
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
003&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;from&nbsp;a&nbsp;heightmap.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
004&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:author&nbsp;&quot;Simon&nbsp;Brooke&quot;}
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
005&nbsp;&nbsp;&nbsp;&nbsp;mw-engine.drainage
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
006&nbsp;&nbsp;&nbsp;&nbsp;(:require&nbsp;[mw-engine.core&nbsp;:refer&nbsp;[run-world]]
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
007&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[mw-engine.heightmap&nbsp;:as&nbsp;heightmap]
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
008&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[mw-engine.utils&nbsp;:refer&nbsp;[get-int-or-zero&nbsp;get-least-cell&nbsp;get-neighbours
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
009&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;get-neighbours-with-property-value
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
010&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;map-world]]))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
011&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
012&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
013&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
014&nbsp;&nbsp;;;;;&nbsp;mw-engine:&nbsp;the&nbsp;state&#x2F;transition&nbsp;engine&nbsp;of&nbsp;MicroWorld.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
015&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
016&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;free&nbsp;software;&nbsp;you&nbsp;can&nbsp;redistribute&nbsp;it&nbsp;and&#x2F;or
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
017&nbsp;&nbsp;;;;;&nbsp;modify&nbsp;it&nbsp;under&nbsp;the&nbsp;terms&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
018&nbsp;&nbsp;;;;;&nbsp;as&nbsp;published&nbsp;by&nbsp;the&nbsp;Free&nbsp;Software&nbsp;Foundation;&nbsp;either&nbsp;version&nbsp;2
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
019&nbsp;&nbsp;;;;;&nbsp;of&nbsp;the&nbsp;License,&nbsp;or&nbsp;(at&nbsp;your&nbsp;option)&nbsp;any&nbsp;later&nbsp;version.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
020&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
021&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;distributed&nbsp;in&nbsp;the&nbsp;hope&nbsp;that&nbsp;it&nbsp;will&nbsp;be&nbsp;useful,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
022&nbsp;&nbsp;;;;;&nbsp;but&nbsp;WITHOUT&nbsp;ANY&nbsp;WARRANTY;&nbsp;without&nbsp;even&nbsp;the&nbsp;implied&nbsp;warranty&nbsp;of
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
023&nbsp;&nbsp;;;;;&nbsp;MERCHANTABILITY&nbsp;or&nbsp;FITNESS&nbsp;FOR&nbsp;A&nbsp;PARTICULAR&nbsp;PURPOSE.&nbsp;&nbsp;See&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
024&nbsp;&nbsp;;;;;&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License&nbsp;for&nbsp;more&nbsp;details.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
025&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
026&nbsp;&nbsp;;;;;&nbsp;You&nbsp;should&nbsp;have&nbsp;received&nbsp;a&nbsp;copy&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
027&nbsp;&nbsp;;;;;&nbsp;along&nbsp;with&nbsp;this&nbsp;program;&nbsp;if&nbsp;not,&nbsp;write&nbsp;to&nbsp;the&nbsp;Free&nbsp;Software
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
028&nbsp;&nbsp;;;;;&nbsp;Foundation,&nbsp;Inc.,&nbsp;51&nbsp;Franklin&nbsp;Street,&nbsp;Fifth&nbsp;Floor,&nbsp;Boston,&nbsp;MA&nbsp;&nbsp;02110-1301,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
029&nbsp;&nbsp;;;;;&nbsp;USA.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
030&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
031&nbsp;&nbsp;;;;;&nbsp;Copyright&nbsp;(C)&nbsp;2014&nbsp;Simon&nbsp;Brooke
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
032&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
033&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
034&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
035&nbsp;&nbsp;
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
036&nbsp;&nbsp;(def&nbsp;^:dynamic&nbsp;*sealevel*&nbsp;10)
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
037&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
038&nbsp;&nbsp;;;&nbsp;forward&nbsp;declaration&nbsp;of&nbsp;flow,&nbsp;to&nbsp;allow&nbsp;for&nbsp;a&nbsp;wee&nbsp;bit&nbsp;of&nbsp;mutual&nbsp;recursion.
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
039&nbsp;&nbsp;(declare&nbsp;flow)
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
040&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
041&nbsp;&nbsp;(defn&nbsp;rainfall
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
042&nbsp;&nbsp;&nbsp;&nbsp;&quot;Compute&nbsp;rainfall&nbsp;for&nbsp;a&nbsp;cell&nbsp;with&nbsp;this&nbsp;`gradient`&nbsp;west-east,&nbsp;given
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
043&nbsp;&nbsp;&nbsp;&nbsp;`remaining`&nbsp;drops&nbsp;to&nbsp;distribute,&nbsp;and&nbsp;this&nbsp;overall&nbsp;map&nbsp;width.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
044&nbsp;&nbsp;&nbsp;&nbsp;[gradient&nbsp;remaining&nbsp;map-width]
</span><br/>
<span class="not-covered" title="0 out of 7 forms covered">
045&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
046&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;if&nbsp;there&#x27;s&nbsp;no&nbsp;rain&nbsp;left&nbsp;in&nbsp;the&nbsp;cloud,&nbsp;it&nbsp;can&#x27;t&nbsp;fall;
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
047&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(zero?&nbsp;remaining)
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
048&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;0
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
049&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(pos?&nbsp;gradient)
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
050&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;rain,&nbsp;on&nbsp;prevailing&nbsp;westerly&nbsp;wind,&nbsp;falls&nbsp;preferentially&nbsp;on&nbsp;rising&nbsp;ground;
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
051&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(int&nbsp;(rand&nbsp;gradient))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
052&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;rain&nbsp;falls&nbsp;randomly&nbsp;across&nbsp;the&nbsp;width&nbsp;of&nbsp;the&nbsp;map...
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
053&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(zero?&nbsp;(int&nbsp;(rand&nbsp;map-width)))&nbsp;1
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
054&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:else
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
055&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;0))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
056&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
057&nbsp;&nbsp;(defn&nbsp;rain-row
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
058&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;a&nbsp;row&nbsp;like&nbsp;this&nbsp;`row`,&nbsp;across&nbsp;which&nbsp;rainfall&nbsp;has&nbsp;been&nbsp;distributed;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
059&nbsp;&nbsp;&nbsp;&nbsp;if&nbsp;`rain-probability`&nbsp;is&nbsp;specified,&nbsp;it&nbsp;is&nbsp;the&nbsp;probable&nbsp;rainfall&nbsp;on&nbsp;a&nbsp;cell
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
060&nbsp;&nbsp;&nbsp;&nbsp;with&nbsp;no&nbsp;gradient.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
061&nbsp;&nbsp;&nbsp;&nbsp;([row]
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
062&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(rain-row&nbsp;row&nbsp;1))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
063&nbsp;&nbsp;&nbsp;&nbsp;([row&nbsp;rain-probability]
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
064&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(rain-row&nbsp;row&nbsp;(count&nbsp;row)&nbsp;0&nbsp;(int&nbsp;(*&nbsp;(count&nbsp;row)&nbsp;rain-probability))))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
065&nbsp;&nbsp;&nbsp;&nbsp;([row&nbsp;map-width&nbsp;previous-altitude&nbsp;drops-in-cloud]
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
066&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
067&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(empty?&nbsp;row)&nbsp;nil
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
068&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(pos?&nbsp;drops-in-cloud)
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
069&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[cell&nbsp;(first&nbsp;row)
</span><br/>
<span class="not-covered" title="0 out of 8 forms covered">
070&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;alt&nbsp;(or&nbsp;(:altitude&nbsp;cell)&nbsp;0)
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
071&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;rising&nbsp;(-&nbsp;alt&nbsp;previous-altitude)
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
072&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;fall&nbsp;(rainfall&nbsp;rising&nbsp;drops-in-cloud&nbsp;map-width)]
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
073&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cons
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
074&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(assoc&nbsp;cell&nbsp;:rainfall&nbsp;fall)
</span><br/>
<span class="not-covered" title="0 out of 10 forms covered">
075&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(rain-row&nbsp;(rest&nbsp;row)&nbsp;map-width&nbsp;alt&nbsp;(-&nbsp;drops-in-cloud&nbsp;fall))))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
076&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:else
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
077&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
078&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;#(assoc&nbsp;%&nbsp;:rainfall&nbsp;0)
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
079&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;row))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
080&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
081&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
082&nbsp;&nbsp;(defn&nbsp;rain-world
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
083&nbsp;&nbsp;&nbsp;&nbsp;&quot;Simulate&nbsp;rainfall&nbsp;on&nbsp;this&nbsp;`world`.&nbsp;TODO:&nbsp;Doesn&#x27;t&nbsp;really&nbsp;work&nbsp;just&nbsp;now&nbsp;-&nbsp;should
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
084&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;rain&nbsp;more&nbsp;on&nbsp;west-facing&nbsp;slopes,&nbsp;and&nbsp;less&nbsp;to&nbsp;the&nbsp;east&nbsp;of&nbsp;high&nbsp;ground&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
085&nbsp;&nbsp;&nbsp;&nbsp;[world]
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
086&nbsp;&nbsp;&nbsp;&nbsp;(map
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
087&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;rain-row
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
088&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;world))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
089&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
090&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
091&nbsp;&nbsp;(defn&nbsp;flow-contributors
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
092&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;a&nbsp;list&nbsp;of&nbsp;the&nbsp;cells&nbsp;in&nbsp;this&nbsp;`world`&nbsp;which&nbsp;are&nbsp;higher&nbsp;than&nbsp;this
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
093&nbsp;&nbsp;&nbsp;&nbsp;`cell`&nbsp;and&nbsp;for&nbsp;which&nbsp;this&nbsp;cell&nbsp;is&nbsp;the&nbsp;lowest&nbsp;neighbour,&nbsp;or&nbsp;which&nbsp;are&nbsp;at&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
094&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;same&nbsp;altitude&nbsp;and&nbsp;have&nbsp;greater&nbsp;flow&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
095&nbsp;&nbsp;&nbsp;&nbsp;[cell&nbsp;world]
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
096&nbsp;&nbsp;&nbsp;&nbsp;(filter&nbsp;#(map?&nbsp;%)
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
097&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
098&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[n]
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
099&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond
</span><br/>
<span class="not-covered" title="0 out of 10 forms covered">
100&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(=&nbsp;cell&nbsp;(get-least-cell&nbsp;(get-neighbours&nbsp;world&nbsp;n)&nbsp;:altitude))&nbsp;n
</span><br/>
<span class="not-covered" title="0 out of 12 forms covered">
101&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(and&nbsp;(=&nbsp;(:altitude&nbsp;cell)&nbsp;(:altitude&nbsp;n))
</span><br/>
<span class="not-covered" title="0 out of 17 forms covered">
102&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&gt;&nbsp;(or&nbsp;(:flow&nbsp;n)&nbsp;0)&nbsp;(or&nbsp;(:flow&nbsp;cell)&nbsp;0)))&nbsp;n))
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
103&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-neighbours-with-property-value
</span><br/>
<span class="not-covered" title="0 out of 7 forms covered">
104&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;world&nbsp;(:x&nbsp;cell)&nbsp;(:y&nbsp;cell)&nbsp;1&nbsp;:altitude
</span><br/>
<span class="not-covered" title="0 out of 9 forms covered">
105&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(or&nbsp;(:altitude&nbsp;cell)&nbsp;0)&nbsp;&gt;=))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
106&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
107&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
108&nbsp;&nbsp;(defn&nbsp;is-hollow
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
109&nbsp;&nbsp;&nbsp;&nbsp;&quot;Detects&nbsp;point&nbsp;hollows&nbsp;-&nbsp;that&nbsp;is,&nbsp;individual&nbsp;cells&nbsp;all&nbsp;of&nbsp;whose&nbsp;neighbours
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
110&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;are&nbsp;higher.&nbsp;Return&nbsp;true&nbsp;if&nbsp;this&nbsp;`cell`&nbsp;has&nbsp;an&nbsp;altitude&nbsp;lower&nbsp;than&nbsp;any&nbsp;of
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
111&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;its&nbsp;neighbours&nbsp;in&nbsp;this&nbsp;`world`&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
112&nbsp;&nbsp;&nbsp;&nbsp;[world&nbsp;cell]
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
113&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;quicker&nbsp;to&nbsp;count&nbsp;the&nbsp;elements&nbsp;of&nbsp;the&nbsp;list&nbsp;and&nbsp;compare&nbsp;equality&nbsp;of&nbsp;numbers
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
114&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;than&nbsp;recursive&nbsp;equality&nbsp;check&nbsp;on&nbsp;members,&nbsp;I&nbsp;think.&nbsp;But&nbsp;worth&nbsp;benchmarking.
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
115&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[neighbours&nbsp;(get-neighbours&nbsp;world&nbsp;cell)
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
116&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;altitude&nbsp;(get-int-or-zero&nbsp;cell&nbsp;:altitude)]
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
117&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(=&nbsp;(count&nbsp;neighbours)
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
118&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(count&nbsp;(get-neighbours-with-property-value
</span><br/>
<span class="covered" title="9 out of 9 forms covered">
119&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;world&nbsp;(:x&nbsp;cell)&nbsp;(:y&nbsp;cell)&nbsp;1&nbsp;:altitude&nbsp;altitude&nbsp;&gt;)))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
120&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
121&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
122&nbsp;&nbsp;(defn&nbsp;flood-hollow
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
123&nbsp;&nbsp;&nbsp;&nbsp;&quot;Raise&nbsp;the&nbsp;altitude&nbsp;of&nbsp;a&nbsp;copy&nbsp;of&nbsp;this&nbsp;`cell`&nbsp;of&nbsp;this&nbsp;`world`&nbsp;to&nbsp;the&nbsp;altitude
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
124&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;of&nbsp;the&nbsp;lowest&nbsp;of&nbsp;its&nbsp;`neighbours`.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
125&nbsp;&nbsp;&nbsp;&nbsp;([_world&nbsp;cell&nbsp;neighbours]
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
126&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[lowest&nbsp;(get-least-cell&nbsp;neighbours&nbsp;:altitude)]
</span><br/>
<span class="covered" title="10 out of 10 forms covered">
127&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:state&nbsp;:water&nbsp;:altitude&nbsp;(:altitude&nbsp;lowest)})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
128&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;cell]
</span><br/>
<span class="covered" title="8 out of 8 forms covered">
129&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(flood-hollow&nbsp;world&nbsp;cell&nbsp;(get-neighbours&nbsp;world&nbsp;cell))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
130&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
131&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
132&nbsp;&nbsp;(defn&nbsp;flood-hollows
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
133&nbsp;&nbsp;&nbsp;&nbsp;&quot;Flood&nbsp;all&nbsp;local&nbsp;hollows&nbsp;in&nbsp;this&nbsp;`world`.&nbsp;At&nbsp;this&nbsp;stage&nbsp;only&nbsp;floods&nbsp;single
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
134&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;cell&nbsp;hollows.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
135&nbsp;&nbsp;&nbsp;&nbsp;[world]
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
136&nbsp;&nbsp;&nbsp;&nbsp;(map-world&nbsp;world
</span><br/>
<span class="covered" title="10 out of 10 forms covered">
137&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;#(if&nbsp;(is-hollow&nbsp;%1&nbsp;%2)&nbsp;(flood-hollow&nbsp;%1&nbsp;%2)&nbsp;%2)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
138&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
139&nbsp;&nbsp;
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
140&nbsp;&nbsp;(def&nbsp;max-altitude&nbsp;255)
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
141&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
142&nbsp;&nbsp;(defn&nbsp;flow-nr
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
143&nbsp;&nbsp;&nbsp;&nbsp;&quot;Experimental&nbsp;non&nbsp;recursive&nbsp;flow&nbsp;algorithm,&nbsp;needs&nbsp;to&nbsp;be&nbsp;run&nbsp;on&nbsp;a&nbsp;world&nbsp;as
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
144&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;many&nbsp;times&nbsp;as&nbsp;there&nbsp;are&nbsp;distinct&nbsp;altitude&nbsp;values.&nbsp;This&nbsp;algorithm&nbsp;works&nbsp;only
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
145&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if&nbsp;applied&nbsp;sequentially&nbsp;from&nbsp;the&nbsp;highest&nbsp;altitude&nbsp;to&nbsp;the&nbsp;lowest,&nbsp;see
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
146&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;`flow-world-nr`.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
147&nbsp;&nbsp;&nbsp;&nbsp;[cell&nbsp;world]
</span><br/>
<span class="not-covered" title="0 out of 9 forms covered">
148&nbsp;&nbsp;&nbsp;&nbsp;(when&nbsp;(=&nbsp;(-&nbsp;max-altitude&nbsp;(get-int-or-zero&nbsp;cell&nbsp;:generation))
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
149&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-int-or-zero&nbsp;cell&nbsp;:altitude))
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
150&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
151&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{:flow&nbsp;(reduce&nbsp;+
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
152&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
153&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;#(+&nbsp;(get-int-or-zero&nbsp;%&nbsp;:rainfall)
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
154&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-int-or-zero&nbsp;%&nbsp;:flow))
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
155&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(flow-contributors&nbsp;cell&nbsp;world)))})))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
156&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
157&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
158&nbsp;&nbsp;(def&nbsp;flow
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
159&nbsp;&nbsp;&nbsp;&nbsp;&quot;Compute&nbsp;the&nbsp;total&nbsp;flow&nbsp;upstream&nbsp;of&nbsp;this&nbsp;`cell`&nbsp;in&nbsp;this&nbsp;`world`,&nbsp;and&nbsp;return&nbsp;a&nbsp;cell&nbsp;identical
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
160&nbsp;&nbsp;&nbsp;&nbsp;to&nbsp;this&nbsp;one&nbsp;but&nbsp;having&nbsp;a&nbsp;value&nbsp;of&nbsp;its&nbsp;flow&nbsp;property&nbsp;set&nbsp;from&nbsp;that&nbsp;computation.&nbsp;The&nbsp;function&nbsp;is
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
161&nbsp;&nbsp;&nbsp;&nbsp;memoised&nbsp;because&nbsp;the&nbsp;consequence&nbsp;of&nbsp;mapping&nbsp;a&nbsp;recursive&nbsp;function&nbsp;across&nbsp;an&nbsp;array&nbsp;is&nbsp;that&nbsp;many
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
162&nbsp;&nbsp;&nbsp;&nbsp;cells&nbsp;will&nbsp;be&nbsp;revisited&nbsp;-&nbsp;potentially&nbsp;many&nbsp;times.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
163&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
164&nbsp;&nbsp;&nbsp;&nbsp;Flow&nbsp;comes&nbsp;from&nbsp;a&nbsp;higher&nbsp;cell&nbsp;to&nbsp;a&nbsp;lower&nbsp;only&nbsp;if&nbsp;the&nbsp;lower&nbsp;is&nbsp;the&nbsp;lowest&nbsp;neighbour&nbsp;of&nbsp;the&nbsp;higher.&quot;
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
165&nbsp;&nbsp;&nbsp;&nbsp;(memoize
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
166&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;world]
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
167&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond
</span><br/>
<span class="not-covered" title="0 out of 8 forms covered">
168&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(not&nbsp;(nil?&nbsp;(:flow&nbsp;cell)))&nbsp;cell
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
169&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&lt;=&nbsp;(or&nbsp;(:altitude&nbsp;cell)&nbsp;0)&nbsp;*sealevel*)&nbsp;cell
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
170&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:else
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
171&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
172&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{:flow&nbsp;(+&nbsp;(:rainfall&nbsp;cell)
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
173&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(apply&nbsp;+
</span><br/>
<span class="not-covered" title="0 out of 9 forms covered">
174&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map&nbsp;(fn&nbsp;[neighbour]&nbsp;(:flow&nbsp;(flow&nbsp;neighbour&nbsp;world)))
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
175&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(flow-contributors&nbsp;cell&nbsp;world))))})))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
176&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
177&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
178&nbsp;&nbsp;(defn&nbsp;flow-world-nr
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
179&nbsp;&nbsp;&nbsp;&nbsp;&quot;Experimental&nbsp;non-recursive&nbsp;flow-world&nbsp;algorithm&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
180&nbsp;&nbsp;&nbsp;&nbsp;[world]
</span><br/>
<span class="not-covered" title="0 out of 8 forms covered">
181&nbsp;&nbsp;&nbsp;&nbsp;(run-world&nbsp;world&nbsp;nil&nbsp;(list&nbsp;flow-nr)&nbsp;max-altitude))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
182&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
183&nbsp;&nbsp;(defn&nbsp;flow-world
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
184&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;a&nbsp;world&nbsp;like&nbsp;this&nbsp;`world`,&nbsp;but&nbsp;with&nbsp;cells&nbsp;tagged&nbsp;with&nbsp;the&nbsp;amount&nbsp;of
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
185&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;water&nbsp;flowing&nbsp;through&nbsp;them.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
186&nbsp;&nbsp;&nbsp;&nbsp;[world]
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
187&nbsp;&nbsp;&nbsp;&nbsp;(map-world&nbsp;(rain-world&nbsp;world)&nbsp;flow))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
188&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
189&nbsp;&nbsp;(defn&nbsp;explore-lake
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
190&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;a&nbsp;sequence&nbsp;of&nbsp;cells&nbsp;starting&nbsp;with&nbsp;this&nbsp;`cell`&nbsp;in&nbsp;this&nbsp;`world`&nbsp;which
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
191&nbsp;&nbsp;&nbsp;&nbsp;form&nbsp;a&nbsp;contiguous&nbsp;lake&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
192&nbsp;&nbsp;&nbsp;&nbsp;[_world&nbsp;_cell]
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
193&nbsp;&nbsp;&nbsp;&nbsp;)
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
194&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
195&nbsp;&nbsp;(defn&nbsp;is-lake?
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
196&nbsp;&nbsp;&nbsp;&nbsp;&quot;If&nbsp;this&nbsp;`cell`&nbsp;in&nbsp;this&nbsp;`world`&nbsp;is&nbsp;not&nbsp;part&nbsp;of&nbsp;a&nbsp;lake,&nbsp;return&nbsp;nil.&nbsp;If&nbsp;it&nbsp;is,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
197&nbsp;&nbsp;&nbsp;&nbsp;return&nbsp;a&nbsp;cell&nbsp;like&nbsp;this&nbsp;`cell`&nbsp;tagged&nbsp;as&nbsp;part&nbsp;of&nbsp;a&nbsp;lake.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
198&nbsp;&nbsp;&nbsp;&nbsp;[world&nbsp;cell]
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
199&nbsp;&nbsp;&nbsp;&nbsp;(if
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
200&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;if&nbsp;it&#x27;s&nbsp;already&nbsp;tagged&nbsp;as&nbsp;a&nbsp;lake,&nbsp;it&#x27;s&nbsp;a&nbsp;lake
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
201&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(:lake&nbsp;cell)&nbsp;cell
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
202&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(let
</span><br/>
<span class="not-covered" title="0 out of 10 forms covered">
203&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[outflow&nbsp;(apply&nbsp;min&nbsp;(map&nbsp;:altitude&nbsp;(get-neighbours&nbsp;world&nbsp;cell)))]
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
204&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(when-not
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
205&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&gt;&nbsp;(:altitude&nbsp;cell)&nbsp;outflow)
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
206&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(assoc&nbsp;cell&nbsp;:lake&nbsp;true)))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
207&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
208&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
209&nbsp;&nbsp;(defn&nbsp;find-lakes
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
210&nbsp;&nbsp;&nbsp;&nbsp;[_world]
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
211&nbsp;&nbsp;&nbsp;&nbsp;)
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
212&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
213&nbsp;&nbsp;(defn&nbsp;run-drainage
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
214&nbsp;&nbsp;&nbsp;&nbsp;&quot;Create&nbsp;a&nbsp;world&nbsp;from&nbsp;the&nbsp;heightmap&nbsp;`hmap`,&nbsp;rain&nbsp;on&nbsp;it,&nbsp;and&nbsp;then&nbsp;compute&nbsp;river
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
215&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;flows.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
216&nbsp;&nbsp;&nbsp;&nbsp;[hmap]
</span><br/>
<span class="not-covered" title="0 out of 9 forms covered">
217&nbsp;&nbsp;&nbsp;&nbsp;(flow-world&nbsp;(rain-world&nbsp;(flood-hollows&nbsp;(heightmap&#x2F;apply-heightmap&nbsp;hmap)))))
</span><br/>
</body>
</html>

View file

@ -0,0 +1,431 @@
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<link rel="stylesheet" href="../coverage.css"/> <title> mw_engine/flow.clj </title>
</head>
<body>
<span class="covered" title="1 out of 1 forms covered">
001&nbsp;&nbsp;(ns&nbsp;mw-engine.flow
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
002&nbsp;&nbsp;&nbsp;&nbsp;&quot;Allow&nbsp;flows&nbsp;of&nbsp;values&nbsp;between&nbsp;cells&nbsp;in&nbsp;the&nbsp;world.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
003&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
004&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;The&nbsp;design&nbsp;here&nbsp;is:&nbsp;a&nbsp;flow&nbsp;object&nbsp;is&nbsp;a&nbsp;map&nbsp;with&nbsp;the&nbsp;following&nbsp;properties:
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
005&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
006&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;1.&nbsp;`:source`,&nbsp;whose&nbsp;value&nbsp;is&nbsp;a&nbsp;location;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
007&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;2.&nbsp;`:destination`,&nbsp;whose&nbsp;value&nbsp;is&nbsp;a&nbsp;location;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
008&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;3.&nbsp;`:property`,&nbsp;whose&nbsp;value&nbsp;is&nbsp;a&nbsp;keyword;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
009&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;4.&nbsp;`:quantity`,&nbsp;whose&nbsp;value&nbsp;is&nbsp;a&nbsp;positive&nbsp;real&nbsp;number.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
010&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
011&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;A&nbsp;location&nbsp;object&nbsp;is&nbsp;a&nbsp;map&nbsp;with&nbsp;the&nbsp;following&nbsp;properties:
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
012&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
013&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;1.&nbsp;`:x`,&nbsp;whose&nbsp;value&nbsp;is&nbsp;a&nbsp;natural&nbsp;number&nbsp;not&nbsp;greater&nbsp;than&nbsp;the&nbsp;extent&nbsp;of&nbsp;the&nbsp;world;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
014&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;2.&nbsp;`:y`,&nbsp;whose&nbsp;value&nbsp;is&nbsp;a&nbsp;natural&nbsp;number&nbsp;not&nbsp;greater&nbsp;than&nbsp;the&nbsp;extent&nbsp;of&nbsp;the&nbsp;world.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
015&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
016&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;To&nbsp;execute&nbsp;a&nbsp;flow&nbsp;is&nbsp;transfer&nbsp;the&nbsp;quantity&nbsp;specified&nbsp;of&nbsp;the&nbsp;property&nbsp;specified
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
017&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;from&nbsp;the&nbsp;cell&nbsp;at&nbsp;the&nbsp;source&nbsp;specified&nbsp;to&nbsp;the&nbsp;cell&nbsp;at&nbsp;the&nbsp;destination&nbsp;specified;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
018&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if&nbsp;the&nbsp;source&nbsp;doesn&#x27;t&nbsp;have&nbsp;sufficient&nbsp;of&nbsp;the&nbsp;property,&nbsp;then&nbsp;all&nbsp;it&nbsp;has&nbsp;should
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
019&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;be&nbsp;transferred,&nbsp;but&nbsp;no&nbsp;more:&nbsp;properties&nbsp;to&nbsp;be&nbsp;flowed&nbsp;cannot&nbsp;be&nbsp;pulled&nbsp;negative.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
020&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
021&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Flowing&nbsp;values&nbsp;through&nbsp;the&nbsp;world&nbsp;is&nbsp;consequently&nbsp;a&nbsp;two&nbsp;stage&nbsp;process:&nbsp;firstly
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
022&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;there&#x27;s&nbsp;a&nbsp;planning&nbsp;stage,&nbsp;in&nbsp;which&nbsp;all&nbsp;the&nbsp;flows&nbsp;to&nbsp;be&nbsp;executed&nbsp;are&nbsp;computed
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
023&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;without&nbsp;changing&nbsp;the&nbsp;world,&nbsp;and&nbsp;then&nbsp;an&nbsp;execution&nbsp;stage,&nbsp;where&nbsp;they&#x27;re&nbsp;all&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
024&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;executed.&nbsp;This&nbsp;namespace&nbsp;deals&nbsp;with&nbsp;mainly&nbsp;with&nbsp;execution.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
025&nbsp;&nbsp;&nbsp;&nbsp;(:require&nbsp;[mw-engine.utils&nbsp;:refer&nbsp;[get-cell&nbsp;get-num&nbsp;in-bounds?&nbsp;merge-cell]]
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
026&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[taoensso.timbre&nbsp;:refer&nbsp;[info&nbsp;warn]]))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
027&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
028&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
029&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
030&nbsp;&nbsp;;;;;&nbsp;mw-engine:&nbsp;the&nbsp;state&#x2F;transition&nbsp;engine&nbsp;of&nbsp;MicroWorld.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
031&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
032&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;free&nbsp;software;&nbsp;you&nbsp;can&nbsp;redistribute&nbsp;it&nbsp;and&#x2F;or
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
033&nbsp;&nbsp;;;;;&nbsp;modify&nbsp;it&nbsp;under&nbsp;the&nbsp;terms&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
034&nbsp;&nbsp;;;;;&nbsp;as&nbsp;published&nbsp;by&nbsp;the&nbsp;Free&nbsp;Software&nbsp;Foundation;&nbsp;either&nbsp;version&nbsp;2
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
035&nbsp;&nbsp;;;;;&nbsp;of&nbsp;the&nbsp;License,&nbsp;or&nbsp;(at&nbsp;your&nbsp;option)&nbsp;any&nbsp;later&nbsp;version.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
036&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
037&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;distributed&nbsp;in&nbsp;the&nbsp;hope&nbsp;that&nbsp;it&nbsp;will&nbsp;be&nbsp;useful,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
038&nbsp;&nbsp;;;;;&nbsp;but&nbsp;WITHOUT&nbsp;ANY&nbsp;WARRANTY;&nbsp;without&nbsp;even&nbsp;the&nbsp;implied&nbsp;warranty&nbsp;of
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
039&nbsp;&nbsp;;;;;&nbsp;MERCHANTABILITY&nbsp;or&nbsp;FITNESS&nbsp;FOR&nbsp;A&nbsp;PARTICULAR&nbsp;PURPOSE.&nbsp;&nbsp;See&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
040&nbsp;&nbsp;;;;;&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License&nbsp;for&nbsp;more&nbsp;details.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
041&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
042&nbsp;&nbsp;;;;;&nbsp;You&nbsp;should&nbsp;have&nbsp;received&nbsp;a&nbsp;copy&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
043&nbsp;&nbsp;;;;;&nbsp;along&nbsp;with&nbsp;this&nbsp;program;&nbsp;if&nbsp;not,&nbsp;write&nbsp;to&nbsp;the&nbsp;Free&nbsp;Software
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
044&nbsp;&nbsp;;;;;&nbsp;Foundation,&nbsp;Inc.,&nbsp;51&nbsp;Franklin&nbsp;Street,&nbsp;Fifth&nbsp;Floor,&nbsp;Boston,&nbsp;MA&nbsp;&nbsp;02110-1301,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
045&nbsp;&nbsp;;;;;&nbsp;USA.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
046&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
047&nbsp;&nbsp;;;;;&nbsp;Copyright&nbsp;(C)&nbsp;2014&nbsp;Simon&nbsp;Brooke
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
048&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
049&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
050&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
051&nbsp;&nbsp;(defn&nbsp;coordinate?
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
052&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;`true`&nbsp;if&nbsp;this&nbsp;object&nbsp;`o`&nbsp;is&nbsp;a&nbsp;valid&nbsp;coordinate&nbsp;with&nbsp;respect&nbsp;to
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
053&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;this&nbsp;`world`,&nbsp;else&nbsp;`false`.&nbsp;Assumes&nbsp;square&nbsp;worlds.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
054&nbsp;&nbsp;&nbsp;&nbsp;[o&nbsp;world]
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
055&nbsp;&nbsp;&nbsp;&nbsp;(try
</span><br/>
<span class="covered" title="14 out of 14 forms covered">
056&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(and&nbsp;(or&nbsp;(zero?&nbsp;o)&nbsp;(pos-int?&nbsp;o))
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
057&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&lt;&nbsp;o&nbsp;(count&nbsp;world)))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
058&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(catch&nbsp;Exception&nbsp;e
</span><br/>
<span class="covered" title="20 out of 20 forms covered">
059&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(warn&nbsp;(format&nbsp;&quot;Not&nbsp;a&nbsp;valid&nbsp;coordinate:&nbsp;%s;&nbsp;%s&quot;&nbsp;o&nbsp;(.getMessage&nbsp;e)))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
060&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;false)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
061&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
062&nbsp;&nbsp;(defn&nbsp;location?
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
063&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;`true`&nbsp;if&nbsp;this&nbsp;object&nbsp;`o`&nbsp;is&nbsp;a&nbsp;location&nbsp;as&nbsp;defined&nbsp;above&nbsp;with&nbsp;respect&nbsp;to
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
064&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;this&nbsp;`world`,&nbsp;else&nbsp;`false`.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
065&nbsp;&nbsp;&nbsp;&nbsp;[o&nbsp;world]
</span><br/>
<span class="partial" title="1 out of 2 forms covered">
066&nbsp;&nbsp;&nbsp;&nbsp;(try
</span><br/>
<span class="partial" title="14 out of 16 forms covered">
067&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(and&nbsp;(map?&nbsp;o)
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
068&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(integer?&nbsp;(:x&nbsp;o))
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
069&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(integer?&nbsp;(:y&nbsp;o))
</span><br/>
<span class="covered" title="8 out of 8 forms covered">
070&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(in-bounds?&nbsp;world&nbsp;(:x&nbsp;o)&nbsp;(:y&nbsp;o)))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
071&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(catch&nbsp;Exception&nbsp;e
</span><br/>
<span class="not-covered" title="0 out of 20 forms covered">
072&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(warn&nbsp;(format&nbsp;&quot;Not&nbsp;a&nbsp;valid&nbsp;location:&nbsp;%s;&nbsp;%s&quot;&nbsp;o&nbsp;(.getMessage&nbsp;e)))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
073&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;false)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
074&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
075&nbsp;&nbsp;(defn&nbsp;flow?
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
076&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;`true`&nbsp;if&nbsp;this&nbsp;object&nbsp;`o`&nbsp;is&nbsp;a&nbsp;flow&nbsp;as&nbsp;defined&nbsp;above&nbsp;with&nbsp;respect&nbsp;to
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
077&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;this&nbsp;`world`,&nbsp;else&nbsp;`false`.&nbsp;Assumes&nbsp;square&nbsp;worlds.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
078&nbsp;&nbsp;&nbsp;&nbsp;[o&nbsp;world]
</span><br/>
<span class="partial" title="1 out of 2 forms covered">
079&nbsp;&nbsp;&nbsp;&nbsp;(try
</span><br/>
<span class="partial" title="16 out of 20 forms covered">
080&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(and&nbsp;(map?&nbsp;o)
</span><br/>
<span class="covered" title="6 out of 6 forms covered">
081&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(location?&nbsp;(:source&nbsp;o)&nbsp;world)
</span><br/>
<span class="covered" title="6 out of 6 forms covered">
082&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(location?&nbsp;(:destination&nbsp;o)&nbsp;world)
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
083&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(keyword?&nbsp;(:property&nbsp;o))
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
084&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(pos?&nbsp;(:quantity&nbsp;o)))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
085&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(catch&nbsp;Exception&nbsp;e
</span><br/>
<span class="not-covered" title="0 out of 20 forms covered">
086&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(warn&nbsp;(format&nbsp;&quot;Not&nbsp;a&nbsp;valid&nbsp;flow:&nbsp;%s;&nbsp;%s&quot;&nbsp;o&nbsp;(.getMessage&nbsp;e)))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
087&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;false)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
088&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
089&nbsp;&nbsp;(defn&nbsp;execute
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
090&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;a&nbsp;world&nbsp;like&nbsp;this&nbsp;`world`,&nbsp;except&nbsp;with&nbsp;the&nbsp;quantity&nbsp;of&nbsp;the&nbsp;property
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
091&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;described&nbsp;in&nbsp;this&nbsp;`flow`&nbsp;object&nbsp;transferred&nbsp;from&nbsp;the&nbsp;source&nbsp;of&nbsp;that&nbsp;flow
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
092&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;to&nbsp;its&nbsp;destination.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
093&nbsp;&nbsp;&nbsp;&nbsp;[world&nbsp;flow]
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
094&nbsp;&nbsp;&nbsp;&nbsp;(try
</span><br/>
<span class="covered" title="6 out of 6 forms covered">
095&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[sx&nbsp;(-&gt;&nbsp;flow&nbsp;:source&nbsp;:x)
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
096&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;sy&nbsp;(-&gt;&nbsp;flow&nbsp;:source&nbsp;:y)
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
097&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;source&nbsp;(get-cell&nbsp;world&nbsp;sx&nbsp;sy)
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
098&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;dx&nbsp;(-&gt;&nbsp;flow&nbsp;:destination&nbsp;:x)
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
099&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;dy&nbsp;(-&gt;&nbsp;flow&nbsp;:destination&nbsp;:y)
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
100&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;dest&nbsp;(get-cell&nbsp;world&nbsp;dx&nbsp;dy)
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
101&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;p&nbsp;(:property&nbsp;flow)
</span><br/>
<span class="covered" title="8 out of 8 forms covered">
102&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;q&nbsp;(min&nbsp;(:quantity&nbsp;flow)&nbsp;(get-num&nbsp;source&nbsp;p))
</span><br/>
<span class="covered" title="9 out of 9 forms covered">
103&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;s&#x27;&nbsp;(assoc&nbsp;source&nbsp;p&nbsp;(-&nbsp;(source&nbsp;p)&nbsp;q))
</span><br/>
<span class="covered" title="10 out of 10 forms covered">
104&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;d&#x27;&nbsp;(assoc&nbsp;dest&nbsp;p&nbsp;(+&nbsp;(get-num&nbsp;dest&nbsp;p)&nbsp;q))]
</span><br/>
<span class="covered" title="6 out of 6 forms covered">
105&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(if&nbsp;(=&nbsp;q&nbsp;(:quantity&nbsp;flow))
</span><br/>
<span class="covered" title="18 out of 18 forms covered">
106&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(info&nbsp;(format&nbsp;&quot;Moving&nbsp;%f&nbsp;units&nbsp;of&nbsp;%s&nbsp;from&nbsp;%d,%d&nbsp;to&nbsp;%d,%d&quot;
</span><br/>
<span class="covered" title="9 out of 9 forms covered">
107&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(float&nbsp;q)&nbsp;(name&nbsp;p)&nbsp;sx&nbsp;sy&nbsp;dx&nbsp;dy))
</span><br/>
<span class="covered" title="18 out of 18 forms covered">
108&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(warn&nbsp;(format&nbsp;&quot;Moving&nbsp;%s&nbsp;from&nbsp;%d,%d&nbsp;to&nbsp;%d,%d;&nbsp;%f&nbsp;units&nbsp;ordered&nbsp;but&nbsp;only&nbsp;%f&nbsp;available&quot;
</span><br/>
<span class="covered" title="13 out of 13 forms covered">
109&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(name&nbsp;p)&nbsp;sx&nbsp;sy&nbsp;dx&nbsp;dy&nbsp;(float&nbsp;(:quantity&nbsp;flow))&nbsp;(float&nbsp;q))))
</span><br/>
<span class="covered" title="7 out of 7 forms covered">
110&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge-cell&nbsp;(merge-cell&nbsp;world&nbsp;s&#x27;)&nbsp;d&#x27;))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
111&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(catch&nbsp;Exception&nbsp;e
</span><br/>
<span class="not-covered" title="0 out of 20 forms covered">
112&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(warn&nbsp;(format&nbsp;&quot;Failed&nbsp;to&nbsp;execute&nbsp;flow&nbsp;%s:&nbsp;%s&quot;&nbsp;flow&nbsp;(.getMessage&nbsp;e)))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
113&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;return&nbsp;the&nbsp;world&nbsp;unmodified.
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
114&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;world)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
115&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
116&nbsp;&nbsp;(defn&nbsp;execute-flows
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
117&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;a&nbsp;world&nbsp;like&nbsp;this&nbsp;`world`,&nbsp;but&nbsp;with&nbsp;each&nbsp;of&nbsp;these&nbsp;flows&nbsp;executed.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
118&nbsp;&nbsp;&nbsp;&nbsp;[world&nbsp;flows]
</span><br/>
<span class="covered" title="12 out of 12 forms covered">
119&nbsp;&nbsp;&nbsp;&nbsp;(reduce&nbsp;execute&nbsp;world&nbsp;(filter&nbsp;#(flow?&nbsp;%&nbsp;world)&nbsp;flows)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
120&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
121&nbsp;&nbsp;;;&nbsp;building&nbsp;blocks&nbsp;for&nbsp;compiled&nbsp;flow&nbsp;rules
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
122&nbsp;&nbsp;
</span><br/>
<span class="covered" title="32 out of 32 forms covered">
123&nbsp;&nbsp;(defmacro&nbsp;create-location
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
124&nbsp;&nbsp;&nbsp;&nbsp;[cell]
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
125&nbsp;&nbsp;&nbsp;&nbsp;`(select-keys&nbsp;~cell&nbsp;[:x&nbsp;:y]))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
126&nbsp;&nbsp;
</span><br/>
<span class="covered" title="56 out of 56 forms covered">
127&nbsp;&nbsp;(defmacro&nbsp;create-flow-quantity
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
128&nbsp;&nbsp;&nbsp;&nbsp;[source&nbsp;dest&nbsp;prop&nbsp;quantity]
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
129&nbsp;&nbsp;&nbsp;&nbsp;`{:source&nbsp;(create-location&nbsp;~source)
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
130&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:destination&nbsp;(create-location&nbsp;~dest)
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
131&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:prop&nbsp;~prop
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
132&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:quantity&nbsp;~quantity})
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
133&nbsp;&nbsp;
</span><br/>
<span class="covered" title="48 out of 48 forms covered">
134&nbsp;&nbsp;(defmacro&nbsp;create-flow-fraction
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
135&nbsp;&nbsp;&nbsp;&nbsp;[source&nbsp;dest&nbsp;prop&nbsp;fraction]
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
136&nbsp;&nbsp;&nbsp;&nbsp;`(create-flow-quantity&nbsp;~source&nbsp;~dest&nbsp;~prop
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
137&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(*&nbsp;~fraction&nbsp;(get-num&nbsp;~source&nbsp;~prop))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
138&nbsp;&nbsp;
</span><br/>
<span class="covered" title="36 out of 36 forms covered">
139&nbsp;&nbsp;(defmacro&nbsp;create-flow-percent
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
140&nbsp;&nbsp;&nbsp;&nbsp;[source&nbsp;dest&nbsp;prop&nbsp;percent]
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
141&nbsp;&nbsp;&nbsp;&nbsp;`(create-flow-fraction&nbsp;~source&nbsp;~dest&nbsp;~prop&nbsp;(&#x2F;&nbsp;~percent&nbsp;100)))
</span><br/>
</body>
</html>

View file

@ -0,0 +1,389 @@
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<link rel="stylesheet" href="../coverage.css"/> <title> mw_engine/heightmap.clj </title>
</head>
<body>
<span class="covered" title="1 out of 1 forms covered">
001&nbsp;&nbsp;(ns&nbsp;^{:doc&nbsp;&quot;Functions&nbsp;to&nbsp;apply&nbsp;a&nbsp;heightmap&nbsp;to&nbsp;a&nbsp;world.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
002&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
003&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Heightmaps&nbsp;are&nbsp;considered&nbsp;only&nbsp;as&nbsp;greyscale&nbsp;images,&nbsp;so&nbsp;colour&nbsp;is&nbsp;redundent
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
004&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(will&nbsp;be&nbsp;ignored).&nbsp;Darker&nbsp;shades&nbsp;are&nbsp;higher.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
005&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:author&nbsp;&quot;Simon&nbsp;Brooke&quot;}
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
006&nbsp;&nbsp;&nbsp;&nbsp;mw-engine.heightmap
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
007&nbsp;&nbsp;&nbsp;&nbsp;(:require&nbsp;[mikera.image.core&nbsp;:refer&nbsp;[load-image&nbsp;filter-image]]
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
008&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[mikera.image.filters&nbsp;:as&nbsp;filters]
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
009&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[mw-engine.utils&nbsp;:refer&nbsp;[get-int&nbsp;get-neighbours&nbsp;map-world]]
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
010&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[mw-engine.world&nbsp;:refer&nbsp;[make-world]]))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
011&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
012&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
013&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
014&nbsp;&nbsp;;;;;&nbsp;mw-engine:&nbsp;the&nbsp;state&#x2F;transition&nbsp;engine&nbsp;of&nbsp;MicroWorld.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
015&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
016&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;free&nbsp;software;&nbsp;you&nbsp;can&nbsp;redistribute&nbsp;it&nbsp;and&#x2F;or
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
017&nbsp;&nbsp;;;;;&nbsp;modify&nbsp;it&nbsp;under&nbsp;the&nbsp;terms&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
018&nbsp;&nbsp;;;;;&nbsp;as&nbsp;published&nbsp;by&nbsp;the&nbsp;Free&nbsp;Software&nbsp;Foundation;&nbsp;either&nbsp;version&nbsp;2
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
019&nbsp;&nbsp;;;;;&nbsp;of&nbsp;the&nbsp;License,&nbsp;or&nbsp;(at&nbsp;your&nbsp;option)&nbsp;any&nbsp;later&nbsp;version.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
020&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
021&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;distributed&nbsp;in&nbsp;the&nbsp;hope&nbsp;that&nbsp;it&nbsp;will&nbsp;be&nbsp;useful,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
022&nbsp;&nbsp;;;;;&nbsp;but&nbsp;WITHOUT&nbsp;ANY&nbsp;WARRANTY;&nbsp;without&nbsp;even&nbsp;the&nbsp;implied&nbsp;warranty&nbsp;of
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
023&nbsp;&nbsp;;;;;&nbsp;MERCHANTABILITY&nbsp;or&nbsp;FITNESS&nbsp;FOR&nbsp;A&nbsp;PARTICULAR&nbsp;PURPOSE.&nbsp;&nbsp;See&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
024&nbsp;&nbsp;;;;;&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License&nbsp;for&nbsp;more&nbsp;details.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
025&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
026&nbsp;&nbsp;;;;;&nbsp;You&nbsp;should&nbsp;have&nbsp;received&nbsp;a&nbsp;copy&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
027&nbsp;&nbsp;;;;;&nbsp;along&nbsp;with&nbsp;this&nbsp;program;&nbsp;if&nbsp;not,&nbsp;write&nbsp;to&nbsp;the&nbsp;Free&nbsp;Software
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
028&nbsp;&nbsp;;;;;&nbsp;Foundation,&nbsp;Inc.,&nbsp;51&nbsp;Franklin&nbsp;Street,&nbsp;Fifth&nbsp;Floor,&nbsp;Boston,&nbsp;MA&nbsp;&nbsp;02110-1301,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
029&nbsp;&nbsp;;;;;&nbsp;USA.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
030&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
031&nbsp;&nbsp;;;;;&nbsp;Copyright&nbsp;(C)&nbsp;2014&nbsp;Simon&nbsp;Brooke
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
032&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
033&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
034&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
035&nbsp;&nbsp;(defn&nbsp;tag-property
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
036&nbsp;&nbsp;&nbsp;&nbsp;&quot;Set&nbsp;the&nbsp;value&nbsp;of&nbsp;this&nbsp;`property`&nbsp;of&nbsp;this&nbsp;cell&nbsp;from&nbsp;the&nbsp;corresponding&nbsp;pixel&nbsp;of&nbsp;this&nbsp;`heightmap`.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
037&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;If&nbsp;the&nbsp;heightmap&nbsp;you&nbsp;supply&nbsp;is&nbsp;smaller&nbsp;than&nbsp;the&nbsp;world,&nbsp;this&nbsp;will&nbsp;break.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
038&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
039&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;not&nbsp;actually&nbsp;used,&nbsp;but&nbsp;present&nbsp;to&nbsp;enable&nbsp;this&nbsp;function&nbsp;to&nbsp;be
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
040&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;passed&nbsp;as&nbsp;an&nbsp;argument&nbsp;to&nbsp;`mw-engine.utils&#x2F;map-world`,&nbsp;q.v.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
041&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`cell`&nbsp;a&nbsp;cell,&nbsp;as&nbsp;discussed&nbsp;in&nbsp;world.clj,&nbsp;q.v.&nbsp;Alternatively,&nbsp;a&nbsp;map;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
042&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`property`&nbsp;the&nbsp;property&nbsp;(normally&nbsp;a&nbsp;keyword)&nbsp;whose&nbsp;value&nbsp;will&nbsp;be&nbsp;set&nbsp;on&nbsp;the&nbsp;cell.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
043&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`heightmap`&nbsp;an&nbsp;(ideally)&nbsp;greyscale&nbsp;image,&nbsp;whose&nbsp;x&nbsp;and&nbsp;y&nbsp;dimensions&nbsp;should
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
044&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;exceed&nbsp;those&nbsp;of&nbsp;the&nbsp;world&nbsp;of&nbsp;which&nbsp;the&nbsp;`cell`&nbsp;forms&nbsp;part.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
045&nbsp;&nbsp;&nbsp;&nbsp;([_&nbsp;cell&nbsp;property&nbsp;heightmap]
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
046&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(tag-property&nbsp;cell&nbsp;property&nbsp;heightmap))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
047&nbsp;&nbsp;&nbsp;&nbsp;([cell&nbsp;property&nbsp;heightmap]
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
048&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
049&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{property
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
050&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(+&nbsp;(get-int&nbsp;cell&nbsp;property)
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
051&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(-&nbsp;256
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
052&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(abs
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
053&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(mod
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
054&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(.getRGB&nbsp;heightmap
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
055&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-int&nbsp;cell&nbsp;:x)
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
056&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-int&nbsp;cell&nbsp;:y))&nbsp;256))))})))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
057&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
058&nbsp;&nbsp;(defn&nbsp;tag-gradient
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
059&nbsp;&nbsp;&nbsp;&nbsp;&quot;Set&nbsp;the&nbsp;`gradient`&nbsp;property&nbsp;of&nbsp;this&nbsp;`cell`&nbsp;of&nbsp;this&nbsp;`world`&nbsp;to&nbsp;the&nbsp;difference&nbsp;in
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
060&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;altitude&nbsp;between&nbsp;its&nbsp;highest&nbsp;and&nbsp;lowest&nbsp;neghbours.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
061&nbsp;&nbsp;&nbsp;&nbsp;[world&nbsp;cell]
</span><br/>
<span class="covered" title="11 out of 11 forms covered">
062&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[heights&nbsp;(remove&nbsp;nil?&nbsp;(map&nbsp;:altitude&nbsp;(get-neighbours&nbsp;world&nbsp;cell)))
</span><br/>
<span class="partial" title="5 out of 6 forms covered">
063&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;highest&nbsp;(cond&nbsp;(empty?&nbsp;heights)&nbsp;0&nbsp;;;&nbsp;shouldn&#x27;t&nbsp;happen
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
064&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:else&nbsp;(apply&nbsp;max&nbsp;heights))
</span><br/>
<span class="partial" title="5 out of 6 forms covered">
065&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;lowest&nbsp;(cond&nbsp;(empty?&nbsp;heights)&nbsp;0&nbsp;;;&nbsp;shouldn&#x27;t
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
066&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:else&nbsp;(apply&nbsp;min&nbsp;heights))
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
067&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;gradient&nbsp;(-&nbsp;highest&nbsp;lowest)]
</span><br/>
<span class="covered" title="6 out of 6 forms covered">
068&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:gradient&nbsp;gradient})))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
069&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
070&nbsp;&nbsp;(defn&nbsp;tag-gradients
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
071&nbsp;&nbsp;&nbsp;&nbsp;&quot;Set&nbsp;the&nbsp;`gradient`&nbsp;property&nbsp;of&nbsp;each&nbsp;cell&nbsp;in&nbsp;this&nbsp;`world`&nbsp;to&nbsp;the&nbsp;difference&nbsp;in
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
072&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;altitude&nbsp;between&nbsp;its&nbsp;highest&nbsp;and&nbsp;lowest&nbsp;neghbours.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
073&nbsp;&nbsp;&nbsp;&nbsp;[world]
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
074&nbsp;&nbsp;&nbsp;&nbsp;(map-world&nbsp;world&nbsp;tag-gradient))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
075&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
076&nbsp;&nbsp;(defn&nbsp;tag-altitude
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
077&nbsp;&nbsp;&nbsp;&nbsp;&quot;Set&nbsp;the&nbsp;altitude&nbsp;of&nbsp;this&nbsp;cell&nbsp;from&nbsp;the&nbsp;corresponding&nbsp;pixel&nbsp;of&nbsp;this&nbsp;heightmap.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
078&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;If&nbsp;the&nbsp;heightmap&nbsp;you&nbsp;supply&nbsp;is&nbsp;smaller&nbsp;than&nbsp;the&nbsp;world,&nbsp;this&nbsp;will&nbsp;break.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
079&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
080&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;not&nbsp;actually&nbsp;used,&nbsp;but&nbsp;present&nbsp;to&nbsp;enable&nbsp;this&nbsp;function&nbsp;to&nbsp;be
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
081&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;passed&nbsp;as&nbsp;an&nbsp;argument&nbsp;to&nbsp;`mw-engine.utils&#x2F;map-world`,&nbsp;q.v.;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
082&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`cell`&nbsp;a&nbsp;cell,&nbsp;as&nbsp;discussed&nbsp;in&nbsp;world.clj,&nbsp;q.v.&nbsp;Alternatively,&nbsp;a&nbsp;map;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
083&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`heightmap`&nbsp;an&nbsp;(ideally)&nbsp;greyscale&nbsp;image,&nbsp;whose&nbsp;x&nbsp;and&nbsp;y&nbsp;dimensions&nbsp;should
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
084&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;exceed&nbsp;those&nbsp;of&nbsp;the&nbsp;world&nbsp;of&nbsp;which&nbsp;the&nbsp;`cell`&nbsp;forms&nbsp;part.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
085&nbsp;&nbsp;&nbsp;&nbsp;([_&nbsp;cell&nbsp;heightmap]
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
086&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(tag-property&nbsp;cell&nbsp;:altitude&nbsp;heightmap))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
087&nbsp;&nbsp;&nbsp;&nbsp;([cell&nbsp;heightmap]
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
088&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(tag-property&nbsp;cell&nbsp;:altitude&nbsp;heightmap)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
089&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
090&nbsp;&nbsp;(defn&nbsp;apply-heightmap
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
091&nbsp;&nbsp;&nbsp;&nbsp;&quot;Apply&nbsp;the&nbsp;image&nbsp;file&nbsp;loaded&nbsp;from&nbsp;this&nbsp;path&nbsp;to&nbsp;this&nbsp;world,&nbsp;and&nbsp;return&nbsp;a&nbsp;world&nbsp;whose
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
092&nbsp;&nbsp;&nbsp;&nbsp;altitudes&nbsp;are&nbsp;modified&nbsp;(added&nbsp;to)&nbsp;by&nbsp;the&nbsp;altitudes&nbsp;in&nbsp;the&nbsp;heightmap.&nbsp;It&nbsp;is&nbsp;assumed&nbsp;that
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
093&nbsp;&nbsp;&nbsp;&nbsp;the&nbsp;heightmap&nbsp;is&nbsp;at&nbsp;least&nbsp;as&nbsp;large&nbsp;in&nbsp;x&nbsp;and&nbsp;y&nbsp;dimensions&nbsp;as&nbsp;the&nbsp;world.&nbsp;Note&nbsp;that,&nbsp;in
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
094&nbsp;&nbsp;&nbsp;&nbsp;addition&nbsp;to&nbsp;setting&nbsp;the&nbsp;`:altitude`&nbsp;of&nbsp;each&nbsp;cell,&nbsp;this&nbsp;function&nbsp;also&nbsp;sets&nbsp;the&nbsp;`:gradient`.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
095&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
096&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;a&nbsp;world,&nbsp;as&nbsp;defined&nbsp;in&nbsp;`world.clj`,&nbsp;q.v.;&nbsp;if&nbsp;world&nbsp;is&nbsp;not&nbsp;supplied,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
097&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;a&nbsp;world&nbsp;the&nbsp;size&nbsp;of&nbsp;the&nbsp;heightmap&nbsp;will&nbsp;be&nbsp;created;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
098&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`imagepath`&nbsp;a&nbsp;file&nbsp;path&nbsp;or&nbsp;URL&nbsp;which&nbsp;indicates&nbsp;an&nbsp;(ideally&nbsp;greyscale)&nbsp;image&nbsp;file.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
099&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;imagepath]
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
100&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[heightmap&nbsp;(filter-image
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
101&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(load-image&nbsp;imagepath)
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
102&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(filters&#x2F;grayscale))]
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
103&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map-world
</span><br/>
<span class="covered" title="7 out of 7 forms covered">
104&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map-world&nbsp;world&nbsp;tag-altitude&nbsp;(list&nbsp;heightmap))
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
105&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;tag-gradient)))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
106&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;([imagepath]
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
107&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[heightmap&nbsp;(filter-image
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
108&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(load-image&nbsp;imagepath)
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
109&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(filters&#x2F;grayscale))
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
110&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;world&nbsp;(make-world&nbsp;(.getWidth&nbsp;heightmap)&nbsp;(.getHeight&nbsp;heightmap))]
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
111&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map-world
</span><br/>
<span class="covered" title="7 out of 7 forms covered">
112&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map-world&nbsp;world&nbsp;tag-altitude&nbsp;(list&nbsp;heightmap))
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
113&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;tag-gradient))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
114&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
115&nbsp;&nbsp;(defn&nbsp;apply-valuemap
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
116&nbsp;&nbsp;&nbsp;&nbsp;&quot;Generalised&nbsp;from&nbsp;apply-heightmap,&nbsp;set&nbsp;an&nbsp;arbitrary&nbsp;property&nbsp;on&nbsp;each&nbsp;cell
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
117&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;of&nbsp;this&nbsp;`world`&nbsp;from&nbsp;the&nbsp;values&nbsp;in&nbsp;this&nbsp;(ideally&nbsp;greyscale)&nbsp;heightmap.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
118&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
119&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;a&nbsp;world,&nbsp;as&nbsp;defined&nbsp;in&nbsp;`world.clj`,&nbsp;q.v.;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
120&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`imagepath`&nbsp;a&nbsp;file&nbsp;path&nbsp;or&nbsp;URL&nbsp;which&nbsp;indicates&nbsp;an&nbsp;(ideally&nbsp;greyscale)&nbsp;image&nbsp;file;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
121&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`property`&nbsp;the&nbsp;property&nbsp;of&nbsp;each&nbsp;cell&nbsp;whose&nbsp;value&nbsp;should&nbsp;be&nbsp;added&nbsp;to&nbsp;from&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
122&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;intensity&nbsp;of&nbsp;the&nbsp;corresponding&nbsp;cell&nbsp;of&nbsp;the&nbsp;image.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
123&nbsp;&nbsp;&nbsp;&nbsp;[world&nbsp;imagepath&nbsp;property]
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
124&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[heightmap&nbsp;(filter-image
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
125&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(load-image&nbsp;imagepath)
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
126&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(filters&#x2F;grayscale))]
</span><br/>
<span class="covered" title="8 out of 8 forms covered">
127&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map-world&nbsp;world&nbsp;tag-property&nbsp;(list&nbsp;property&nbsp;heightmap))))
</span><br/>
</body>
</html>

View file

@ -0,0 +1,560 @@
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<link rel="stylesheet" href="../coverage.css"/> <title> mw_engine/natural_rules.clj </title>
</head>
<body>
<span class="covered" title="1 out of 1 forms covered">
001&nbsp;&nbsp;(ns&nbsp;^{:doc&nbsp;&quot;A&nbsp;set&nbsp;of&nbsp;MicroWorld&nbsp;rules&nbsp;describing&nbsp;a&nbsp;simplified&nbsp;natural&nbsp;ecosystem.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
002&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
003&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Since&nbsp;the&nbsp;completion&nbsp;of&nbsp;the&nbsp;rule&nbsp;language&nbsp;this&nbsp;is&nbsp;more&nbsp;or&nbsp;less&nbsp;obsolete&nbsp;-
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
004&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;there&nbsp;are&nbsp;still&nbsp;a&nbsp;few&nbsp;things&nbsp;that&nbsp;you&nbsp;can&nbsp;do&nbsp;with&nbsp;rules&nbsp;written&nbsp;in&nbsp;Clojure
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
005&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;that&nbsp;you&nbsp;can&#x27;t&nbsp;do&nbsp;in&nbsp;the&nbsp;rule&nbsp;language,&nbsp;but&nbsp;not&nbsp;many&nbsp;and&nbsp;I&nbsp;doubt&nbsp;they&#x27;re
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
006&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;important.&nbsp;&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
007&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:author&nbsp;&quot;&nbsp;Simon&nbsp;Brooke&nbsp;&quot;}
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
008&nbsp;&nbsp;&nbsp;&nbsp;mw-engine.natural-rules
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
009&nbsp;&nbsp;&nbsp;&nbsp;(:require&nbsp;[mw-engine.utils&nbsp;:refer&nbsp;[get-int&nbsp;get-neighbours&nbsp;get-neighbours-with-state&nbsp;member?]]))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
010&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
011&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
012&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
013&nbsp;&nbsp;;;;;&nbsp;mw-engine:&nbsp;the&nbsp;state&#x2F;transition&nbsp;engine&nbsp;of&nbsp;MicroWorld.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
014&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
015&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;free&nbsp;software;&nbsp;you&nbsp;can&nbsp;redistribute&nbsp;it&nbsp;and&#x2F;or
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
016&nbsp;&nbsp;;;;;&nbsp;modify&nbsp;it&nbsp;under&nbsp;the&nbsp;terms&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
017&nbsp;&nbsp;;;;;&nbsp;as&nbsp;published&nbsp;by&nbsp;the&nbsp;Free&nbsp;Software&nbsp;Foundation;&nbsp;either&nbsp;version&nbsp;2
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
018&nbsp;&nbsp;;;;;&nbsp;of&nbsp;the&nbsp;License,&nbsp;or&nbsp;(at&nbsp;your&nbsp;option)&nbsp;any&nbsp;later&nbsp;version.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
019&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
020&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;distributed&nbsp;in&nbsp;the&nbsp;hope&nbsp;that&nbsp;it&nbsp;will&nbsp;be&nbsp;useful,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
021&nbsp;&nbsp;;;;;&nbsp;but&nbsp;WITHOUT&nbsp;ANY&nbsp;WARRANTY;&nbsp;without&nbsp;even&nbsp;the&nbsp;implied&nbsp;warranty&nbsp;of
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
022&nbsp;&nbsp;;;;;&nbsp;MERCHANTABILITY&nbsp;or&nbsp;FITNESS&nbsp;FOR&nbsp;A&nbsp;PARTICULAR&nbsp;PURPOSE.&nbsp;&nbsp;See&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
023&nbsp;&nbsp;;;;;&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License&nbsp;for&nbsp;more&nbsp;details.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
024&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
025&nbsp;&nbsp;;;;;&nbsp;You&nbsp;should&nbsp;have&nbsp;received&nbsp;a&nbsp;copy&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
026&nbsp;&nbsp;;;;;&nbsp;along&nbsp;with&nbsp;this&nbsp;program;&nbsp;if&nbsp;not,&nbsp;write&nbsp;to&nbsp;the&nbsp;Free&nbsp;Software
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
027&nbsp;&nbsp;;;;;&nbsp;Foundation,&nbsp;Inc.,&nbsp;51&nbsp;Franklin&nbsp;Street,&nbsp;Fifth&nbsp;Floor,&nbsp;Boston,&nbsp;MA&nbsp;&nbsp;02110-1301,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
028&nbsp;&nbsp;;;;;&nbsp;USA.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
029&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
030&nbsp;&nbsp;;;;;&nbsp;Copyright&nbsp;(C)&nbsp;2014&nbsp;Simon&nbsp;Brooke
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
031&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
032&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
033&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
034&nbsp;&nbsp;;;&nbsp;treeline&nbsp;at&nbsp;arbitrary&nbsp;altitude.
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
035&nbsp;&nbsp;(def&nbsp;treeline&nbsp;150)
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
036&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
037&nbsp;&nbsp;;;&nbsp;waterline&nbsp;also&nbsp;at&nbsp;arbitrary&nbsp;altitude.
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
038&nbsp;&nbsp;(def&nbsp;waterline&nbsp;10)
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
039&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
040&nbsp;&nbsp;;;&nbsp;and&nbsp;finally&nbsp;snowline&nbsp;is&nbsp;also&nbsp;arbitrary.
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
041&nbsp;&nbsp;(def&nbsp;snowline&nbsp;200)
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
042&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
043&nbsp;&nbsp;;;&nbsp;Rare&nbsp;chance&nbsp;of&nbsp;lightning&nbsp;strikes
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
044&nbsp;&nbsp;(def&nbsp;lightning-probability&nbsp;500)
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
045&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
046&nbsp;&nbsp;;;&nbsp;rules&nbsp;describing&nbsp;vegetation
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
047&nbsp;&nbsp;(def&nbsp;vegetation-rules
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
048&nbsp;&nbsp;&nbsp;&nbsp;(list
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
049&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;Randomly,&nbsp;birds&nbsp;plant&nbsp;tree&nbsp;seeds&nbsp;into&nbsp;grassland.
</span><br/>
<span class="partial" title="1 out of 23 forms covered">
050&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]&nbsp;(cond&nbsp;(and&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:grassland)(&lt;&nbsp;(rand&nbsp;10)&nbsp;1))(merge&nbsp;cell&nbsp;{:state&nbsp;:heath})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
051&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;heath&nbsp;below&nbsp;the&nbsp;treeline&nbsp;grows&nbsp;gradually&nbsp;into&nbsp;forest,&nbsp;providing&nbsp;browsing&nbsp;pressure&nbsp;is&nbsp;not&nbsp;to&nbsp;high
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
052&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
053&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(and
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
054&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:heath)
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
055&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;browsing&nbsp;limit&nbsp;really&nbsp;ought&nbsp;to&nbsp;vary&nbsp;with&nbsp;soil&nbsp;fertility,&nbsp;but...
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
056&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&lt;&nbsp;(+&nbsp;(get-int&nbsp;cell&nbsp;:deer)(get-int&nbsp;cell&nbsp;:sheep))&nbsp;6)
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
057&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&lt;&nbsp;(get-int&nbsp;cell&nbsp;:altitude)&nbsp;treeline))
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
058&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:state&nbsp;:scrub})))
</span><br/>
<span class="partial" title="1 out of 14 forms covered">
059&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]&nbsp;(cond&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:scrub)&nbsp;(merge&nbsp;cell&nbsp;{:state&nbsp;:forest})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
060&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;Forest&nbsp;on&nbsp;fertile&nbsp;land&nbsp;grows&nbsp;to&nbsp;climax
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
061&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
062&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
063&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(and
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
064&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:forest)
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
065&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&gt;&nbsp;(get-int&nbsp;cell&nbsp;:fertility)&nbsp;10))
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
066&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:state&nbsp;:climax})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
067&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;Climax&nbsp;forest&nbsp;occasionally&nbsp;catches&nbsp;fire&nbsp;(e.g.&nbsp;lightning&nbsp;strikes)
</span><br/>
<span class="partial" title="1 out of 23 forms covered">
068&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]&nbsp;(cond&nbsp;(and&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:climax)(&lt;&nbsp;(rand&nbsp;lightning-probability)&nbsp;1))&nbsp;(merge&nbsp;cell&nbsp;{:state&nbsp;:fire})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
069&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;Climax&nbsp;forest&nbsp;neighbouring&nbsp;fires&nbsp;is&nbsp;likely&nbsp;to&nbsp;catch&nbsp;fire
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
070&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;world]
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
071&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond
</span><br/>
<span class="not-covered" title="0 out of 14 forms covered">
072&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(and&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:climax)
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
073&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&lt;&nbsp;(rand&nbsp;3)&nbsp;1)
</span><br/>
<span class="not-covered" title="0 out of 14 forms covered">
074&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(not&nbsp;(empty?&nbsp;(get-neighbours-with-state&nbsp;world&nbsp;(:x&nbsp;cell)&nbsp;(:y&nbsp;cell)&nbsp;1&nbsp;:fire))))
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
075&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:state&nbsp;:fire})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
076&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;After&nbsp;fire&nbsp;we&nbsp;get&nbsp;waste
</span><br/>
<span class="partial" title="1 out of 14 forms covered">
077&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]&nbsp;(cond&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:fire)&nbsp;(merge&nbsp;cell&nbsp;{:state&nbsp;:waste})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
078&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;And&nbsp;after&nbsp;waste&nbsp;we&nbsp;get&nbsp;pioneer&nbsp;species;&nbsp;if&nbsp;there&#x27;s&nbsp;a&nbsp;woodland&nbsp;seed
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
079&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;source,&nbsp;it&#x27;s&nbsp;going&nbsp;to&nbsp;be&nbsp;heath,&nbsp;otherwise&nbsp;grassland.
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
080&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;world]
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
081&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond
</span><br/>
<span class="not-covered" title="0 out of 10 forms covered">
082&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(and&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:waste)
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
083&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(not
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
084&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(empty?
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
085&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(flatten
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
086&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(list
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
087&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-neighbours-with-state&nbsp;world&nbsp;(:x&nbsp;cell)&nbsp;(:y&nbsp;cell)&nbsp;1&nbsp;:scrub)
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
088&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-neighbours-with-state&nbsp;world&nbsp;(:x&nbsp;cell)&nbsp;(:y&nbsp;cell)&nbsp;1&nbsp;:forest)
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
089&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-neighbours-with-state&nbsp;world&nbsp;(:x&nbsp;cell)&nbsp;(:y&nbsp;cell)&nbsp;1&nbsp;:climax))))))
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
090&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:state&nbsp;:heath})))
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
091&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]
</span><br/>
<span class="not-covered" title="0 out of 7 forms covered">
092&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:waste)
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
093&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:state&nbsp;:grassland})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
094&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;Forest&nbsp;increases&nbsp;soil&nbsp;fertility
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
095&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]
</span><br/>
<span class="not-covered" title="0 out of 8 forms covered">
096&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(member?&nbsp;(:state&nbsp;cell)&nbsp;&#x27;(:forest&nbsp;:climax))
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
097&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:fertility&nbsp;(+&nbsp;(get-int&nbsp;cell&nbsp;:fertility)&nbsp;1)})))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
098&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
099&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
100&nbsp;&nbsp;;;&nbsp;rules&nbsp;describing&nbsp;herbivore&nbsp;behaviour
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
101&nbsp;&nbsp;(def&nbsp;herbivore-rules
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
102&nbsp;&nbsp;&nbsp;&nbsp;(list
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
103&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;if&nbsp;there&nbsp;are&nbsp;too&nbsp;many&nbsp;deer&nbsp;for&nbsp;the&nbsp;fertility&nbsp;of&nbsp;the&nbsp;area&nbsp;to&nbsp;sustain,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
104&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;some&nbsp;die&nbsp;or&nbsp;move&nbsp;on.
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
105&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
106&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(&gt;&nbsp;(get-int&nbsp;cell&nbsp;:deer)&nbsp;(get-int&nbsp;cell&nbsp;:fertility))
</span><br/>
<span class="not-covered" title="0 out of 9 forms covered">
107&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:deer&nbsp;(get-int&nbsp;cell&nbsp;:fertility)})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
108&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;deer&nbsp;arrive&nbsp;occasionally&nbsp;at&nbsp;the&nbsp;edge&nbsp;of&nbsp;the&nbsp;map.
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
109&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;world]
</span><br/>
<span class="not-covered" title="0 out of 23 forms covered">
110&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(and&nbsp;(&lt;&nbsp;(count&nbsp;(get-neighbours&nbsp;world&nbsp;cell))&nbsp;8)
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
111&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&lt;&nbsp;(rand&nbsp;50)&nbsp;1)
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
112&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&gt;&nbsp;(get-int&nbsp;cell&nbsp;:fertility)&nbsp;0)
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
113&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(=&nbsp;(get-int&nbsp;cell&nbsp;:deer)&nbsp;0))
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
114&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:deer&nbsp;2})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
115&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;deer&nbsp;gradually&nbsp;spread&nbsp;through&nbsp;the&nbsp;world&nbsp;by&nbsp;breeding&nbsp;or&nbsp;migrating.
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
116&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;world]
</span><br/>
<span class="not-covered" title="0 out of 15 forms covered">
117&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[n&nbsp;(apply&nbsp;+&nbsp;(map&nbsp;#(get-int&nbsp;%&nbsp;:deer)&nbsp;(get-neighbours&nbsp;world&nbsp;cell)))]
</span><br/>
<span class="not-covered" title="0 out of 12 forms covered">
118&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(and
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
119&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&gt;&nbsp;(get-int&nbsp;cell&nbsp;:fertility)&nbsp;0)
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
120&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(=&nbsp;(get-int&nbsp;cell&nbsp;:deer)&nbsp;0)
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
121&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&gt;=&nbsp;n&nbsp;2))
</span><br/>
<span class="not-covered" title="0 out of 9 forms covered">
122&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:deer&nbsp;(int&nbsp;(&#x2F;&nbsp;n&nbsp;2))}))))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
123&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;deer&nbsp;breed.
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
124&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
125&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
126&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&gt;=&nbsp;(get-int&nbsp;cell&nbsp;:deer)&nbsp;2)
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
127&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:deer&nbsp;(int&nbsp;(*&nbsp;(:deer&nbsp;cell)&nbsp;2))})))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
128&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
129&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;rules&nbsp;describing&nbsp;predator&nbsp;behaviour
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
130&nbsp;&nbsp;&nbsp;&nbsp;(def&nbsp;predator-rules
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
131&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(list
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
132&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;wolves&nbsp;eat&nbsp;deer
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
133&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
134&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
135&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&gt;=&nbsp;(get-int&nbsp;cell&nbsp;:wolves)&nbsp;1)
</span><br/>
<span class="not-covered" title="0 out of 16 forms covered">
136&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:deer&nbsp;(max&nbsp;0&nbsp;(-&nbsp;(get-int&nbsp;cell&nbsp;:deer)&nbsp;(get-int&nbsp;cell&nbsp;:wolves)))})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
137&nbsp;&nbsp;;;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;not&nbsp;more&nbsp;than&nbsp;eight&nbsp;wolves&nbsp;in&nbsp;a&nbsp;pack,&nbsp;for&nbsp;now&nbsp;(hack&nbsp;because&nbsp;wolves&nbsp;are&nbsp;not&nbsp;dying)
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
138&nbsp;&nbsp;;;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;world]
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
139&nbsp;&nbsp;;;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(&gt;&nbsp;(get-int&nbsp;cell&nbsp;:wolves)&nbsp;8)&nbsp;(merge&nbsp;cell&nbsp;{:wolves&nbsp;8})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
140&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;if&nbsp;there&nbsp;are&nbsp;not&nbsp;enough&nbsp;deer&nbsp;to&nbsp;sustain&nbsp;the&nbsp;get-int&nbsp;of&nbsp;wolves,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
141&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;some&nbsp;wolves&nbsp;die&nbsp;or&nbsp;move&nbsp;on.&nbsp;(doesn&#x27;t&nbsp;seem&nbsp;to&nbsp;be&nbsp;working?)
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
142&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
143&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(&gt;&nbsp;(get-int&nbsp;cell&nbsp;:wolves)&nbsp;(get-int&nbsp;cell&nbsp;:deer))
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
144&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:wolves&nbsp;0})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
145&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;wolves&nbsp;arrive&nbsp;occasionally&nbsp;at&nbsp;the&nbsp;edge&nbsp;of&nbsp;the&nbsp;map.
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
146&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;world]
</span><br/>
<span class="not-covered" title="0 out of 23 forms covered">
147&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(and&nbsp;(&lt;&nbsp;(count&nbsp;(get-neighbours&nbsp;world&nbsp;cell))&nbsp;8)
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
148&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&lt;&nbsp;(rand&nbsp;50)&nbsp;1)
</span><br/>
<span class="not-covered" title="0 out of 7 forms covered">
149&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(not&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:water))
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
150&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(=&nbsp;(get-int&nbsp;cell&nbsp;:wolves)&nbsp;0))
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
151&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:wolves&nbsp;2})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
152&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;wolves&nbsp;gradually&nbsp;spread&nbsp;through&nbsp;the&nbsp;world&nbsp;by&nbsp;breeding&nbsp;or&nbsp;migrating.
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
153&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;world]
</span><br/>
<span class="not-covered" title="0 out of 15 forms covered">
154&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[n&nbsp;(apply&nbsp;+&nbsp;(map&nbsp;#(get-int&nbsp;%&nbsp;:wolves)&nbsp;(get-neighbours&nbsp;world&nbsp;cell)))]
</span><br/>
<span class="not-covered" title="0 out of 12 forms covered">
155&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(and
</span><br/>
<span class="not-covered" title="0 out of 7 forms covered">
156&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(not&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:water))
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
157&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(=&nbsp;(get-int&nbsp;cell&nbsp;:wolves)&nbsp;0)
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
158&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&gt;=&nbsp;n&nbsp;2))
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
159&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:wolves&nbsp;2}))))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
160&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;wolves&nbsp;breed.
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
161&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
162&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
163&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(&gt;=&nbsp;(get-int&nbsp;cell&nbsp;:wolves)&nbsp;2)
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
164&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:wolves&nbsp;(int&nbsp;(*&nbsp;(:wolves&nbsp;cell)&nbsp;2))})))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
165&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
166&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
167&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;rules&nbsp;which&nbsp;initialise&nbsp;the&nbsp;world
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
168&nbsp;&nbsp;&nbsp;&nbsp;(def&nbsp;init-rules
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
169&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(list
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
170&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;below&nbsp;the&nbsp;waterline,&nbsp;we&nbsp;have&nbsp;water.
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
171&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]
</span><br/>
<span class="not-covered" title="0 out of 23 forms covered">
172&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(and&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:new)&nbsp;(&lt;&nbsp;(get-int&nbsp;cell&nbsp;:altitude)&nbsp;waterline))&nbsp;(merge&nbsp;cell&nbsp;{:state&nbsp;:water})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
173&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;above&nbsp;the&nbsp;snowline,&nbsp;we&nbsp;have&nbsp;snow.
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
174&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]
</span><br/>
<span class="not-covered" title="0 out of 23 forms covered">
175&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(and&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:new)&nbsp;(&gt;&nbsp;(get-int&nbsp;cell&nbsp;:altitude)&nbsp;snowline))&nbsp;(merge&nbsp;cell&nbsp;{:state&nbsp;:snow})))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
176&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;;;&nbsp;in&nbsp;between,&nbsp;we&nbsp;have&nbsp;a&nbsp;wasteland.
</span><br/>
<span class="partial" title="1 out of 14 forms covered">
177&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[cell&nbsp;_]&nbsp;(cond&nbsp;(=&nbsp;(:state&nbsp;cell)&nbsp;:new)&nbsp;(merge&nbsp;cell&nbsp;{:state&nbsp;:grassland})))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
178&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
179&nbsp;&nbsp;
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
180&nbsp;&nbsp;(def&nbsp;natural-rules&nbsp;(flatten
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
181&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(list
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
182&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;vegetation-rules
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
183&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;herbivore-rules
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
184&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;predator-rules)))
</span><br/>
</body>
</html>

View file

@ -0,0 +1,911 @@
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<link rel="stylesheet" href="../coverage.css"/> <title> mw_engine/utils.clj </title>
</head>
<body>
<span class="covered" title="1 out of 1 forms covered">
001&nbsp;&nbsp;(ns&nbsp;^{:doc&nbsp;&quot;&nbsp;Utility&nbsp;functions&nbsp;needed&nbsp;by&nbsp;MicroWorld&nbsp;and,&nbsp;specifically,&nbsp;in&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
002&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;interpretation&nbsp;of&nbsp;MicroWorld&nbsp;rule.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
003&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:author&nbsp;&quot;Simon&nbsp;Brooke&quot;}
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
004&nbsp;&nbsp;&nbsp;mw-engine.utils
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
005&nbsp;&nbsp;&nbsp;&nbsp;(:require
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
006&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[clojure.math.combinatorics&nbsp;:as&nbsp;combo]))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
007&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
008&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
009&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
010&nbsp;&nbsp;;;;;&nbsp;mw-engine:&nbsp;the&nbsp;state&#x2F;transition&nbsp;engine&nbsp;of&nbsp;MicroWorld.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
011&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
012&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;free&nbsp;software;&nbsp;you&nbsp;can&nbsp;redistribute&nbsp;it&nbsp;and&#x2F;or
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
013&nbsp;&nbsp;;;;;&nbsp;modify&nbsp;it&nbsp;under&nbsp;the&nbsp;terms&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
014&nbsp;&nbsp;;;;;&nbsp;as&nbsp;published&nbsp;by&nbsp;the&nbsp;Free&nbsp;Software&nbsp;Foundation;&nbsp;either&nbsp;version&nbsp;2
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
015&nbsp;&nbsp;;;;;&nbsp;of&nbsp;the&nbsp;License,&nbsp;or&nbsp;(at&nbsp;your&nbsp;option)&nbsp;any&nbsp;later&nbsp;version.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
016&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
017&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;distributed&nbsp;in&nbsp;the&nbsp;hope&nbsp;that&nbsp;it&nbsp;will&nbsp;be&nbsp;useful,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
018&nbsp;&nbsp;;;;;&nbsp;but&nbsp;WITHOUT&nbsp;ANY&nbsp;WARRANTY;&nbsp;without&nbsp;even&nbsp;the&nbsp;implied&nbsp;warranty&nbsp;of
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
019&nbsp;&nbsp;;;;;&nbsp;MERCHANTABILITY&nbsp;or&nbsp;FITNESS&nbsp;FOR&nbsp;A&nbsp;PARTICULAR&nbsp;PURPOSE.&nbsp;&nbsp;See&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
020&nbsp;&nbsp;;;;;&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License&nbsp;for&nbsp;more&nbsp;details.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
021&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
022&nbsp;&nbsp;;;;;&nbsp;You&nbsp;should&nbsp;have&nbsp;received&nbsp;a&nbsp;copy&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
023&nbsp;&nbsp;;;;;&nbsp;along&nbsp;with&nbsp;this&nbsp;program;&nbsp;if&nbsp;not,&nbsp;write&nbsp;to&nbsp;the&nbsp;Free&nbsp;Software
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
024&nbsp;&nbsp;;;;;&nbsp;Foundation,&nbsp;Inc.,&nbsp;51&nbsp;Franklin&nbsp;Street,&nbsp;Fifth&nbsp;Floor,&nbsp;Boston,&nbsp;MA&nbsp;&nbsp;02110-1301,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
025&nbsp;&nbsp;;;;;&nbsp;USA.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
026&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
027&nbsp;&nbsp;;;;;&nbsp;Copyright&nbsp;(C)&nbsp;2014&nbsp;Simon&nbsp;Brooke
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
028&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
029&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
030&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
031&nbsp;&nbsp;(defn&nbsp;member?
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
032&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;&#x27;true&#x27;&nbsp;if&nbsp;elt&nbsp;is&nbsp;a&nbsp;member&nbsp;of&nbsp;col,&nbsp;else&nbsp;&#x27;false&#x27;.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
033&nbsp;&nbsp;&nbsp;&nbsp;[elt&nbsp;col]&nbsp;
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
034&nbsp;&nbsp;&nbsp;&nbsp;(contains?&nbsp;(set&nbsp;col)&nbsp;elt))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
035&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
036&nbsp;&nbsp;(defn&nbsp;get-int-or-zero
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
037&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;the&nbsp;value&nbsp;of&nbsp;this&nbsp;`property`&nbsp;from&nbsp;this&nbsp;`map`&nbsp;if&nbsp;it&nbsp;is&nbsp;a&nbsp;integer;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
038&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;otherwise&nbsp;return&nbsp;zero.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
039&nbsp;&nbsp;&nbsp;&nbsp;[map&nbsp;property]
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
040&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[value&nbsp;(map&nbsp;property)]
</span><br/>
<span class="partial" title="5 out of 6 forms covered">
041&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(if&nbsp;(integer?&nbsp;value)&nbsp;value&nbsp;0)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
042&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
043&nbsp;&nbsp;(defn&nbsp;init-generation
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
044&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;a&nbsp;cell&nbsp;like&nbsp;this&nbsp;`cell`,&nbsp;but&nbsp;having&nbsp;a&nbsp;value&nbsp;for&nbsp;:generation,&nbsp;zero&nbsp;if
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
045&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;the&nbsp;cell&nbsp;passed&nbsp;had&nbsp;no&nbsp;integer&nbsp;value&nbsp;for&nbsp;generation,&nbsp;otherwise&nbsp;the&nbsp;value
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
046&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;taken&nbsp;from&nbsp;the&nbsp;cell&nbsp;passed.&nbsp;The&nbsp;`world`&nbsp;argument&nbsp;is&nbsp;present&nbsp;only&nbsp;for
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
047&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;consistency&nbsp;with&nbsp;the&nbsp;rule&nbsp;engine&nbsp;and&nbsp;is&nbsp;ignored.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
048&nbsp;&nbsp;&nbsp;&nbsp;[_&nbsp;cell]
</span><br/>
<span class="not-covered" title="0 out of 9 forms covered">
049&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{:generation&nbsp;(get-int-or-zero&nbsp;cell&nbsp;:generation)}))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
050&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
051&nbsp;&nbsp;(defn&nbsp;in-bounds
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
052&nbsp;&nbsp;&nbsp;&nbsp;&quot;True&nbsp;if&nbsp;x,&nbsp;y&nbsp;are&nbsp;in&nbsp;bounds&nbsp;for&nbsp;this&nbsp;world&nbsp;(i.e.,&nbsp;there&nbsp;is&nbsp;a&nbsp;cell&nbsp;at&nbsp;x,&nbsp;y)
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
053&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else&nbsp;false.&nbsp;*DEPRECATED*:&nbsp;it&#x27;s&nbsp;a&nbsp;predicate,&nbsp;prefer&nbsp;`in-bounds?`.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
054&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
055&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;a&nbsp;world&nbsp;as&nbsp;defined&nbsp;in&nbsp;[world.clj](mw-engine.world.html);
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
056&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`x`&nbsp;a&nbsp;number&nbsp;which&nbsp;may&nbsp;or&nbsp;may&nbsp;not&nbsp;be&nbsp;a&nbsp;valid&nbsp;x&nbsp;coordinate&nbsp;within&nbsp;that&nbsp;world;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
057&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`y`&nbsp;a&nbsp;number&nbsp;which&nbsp;may&nbsp;or&nbsp;may&nbsp;not&nbsp;be&nbsp;a&nbsp;valid&nbsp;y&nbsp;coordinate&nbsp;within&nbsp;that&nbsp;world.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
058&nbsp;&nbsp;&nbsp;&nbsp;{:deprecated&nbsp;&quot;1.1.7&quot;}
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
059&nbsp;&nbsp;&nbsp;&nbsp;[world&nbsp;x&nbsp;y]
</span><br/>
<span class="not-covered" title="0 out of 28 forms covered">
060&nbsp;&nbsp;&nbsp;&nbsp;(and&nbsp;(&gt;=&nbsp;x&nbsp;0)&nbsp;(&gt;=&nbsp;y&nbsp;0)&nbsp;(&lt;&nbsp;y&nbsp;(count&nbsp;world))&nbsp;(&lt;&nbsp;x&nbsp;(count&nbsp;(first&nbsp;world)))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
061&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
062&nbsp;&nbsp;(defn&nbsp;in-bounds?
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
063&nbsp;&nbsp;&nbsp;&nbsp;&quot;True&nbsp;if&nbsp;x,&nbsp;y&nbsp;are&nbsp;in&nbsp;bounds&nbsp;for&nbsp;this&nbsp;world&nbsp;(i.e.,&nbsp;there&nbsp;is&nbsp;a&nbsp;cell&nbsp;at&nbsp;x,&nbsp;y)
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
064&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else&nbsp;false.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
065&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
066&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;a&nbsp;world&nbsp;as&nbsp;defined&nbsp;in&nbsp;[world.clj](mw-engine.world.html);
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
067&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`x`&nbsp;a&nbsp;number&nbsp;which&nbsp;may&nbsp;or&nbsp;may&nbsp;not&nbsp;be&nbsp;a&nbsp;valid&nbsp;x&nbsp;coordinate&nbsp;within&nbsp;that&nbsp;world;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
068&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`y`&nbsp;a&nbsp;number&nbsp;which&nbsp;may&nbsp;or&nbsp;may&nbsp;not&nbsp;be&nbsp;a&nbsp;valid&nbsp;y&nbsp;coordinate&nbsp;within&nbsp;that&nbsp;world.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
069&nbsp;&nbsp;&nbsp;&nbsp;{:added&nbsp;&quot;1.1.7&quot;}
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
070&nbsp;&nbsp;&nbsp;&nbsp;[world&nbsp;x&nbsp;y]
</span><br/>
<span class="covered" title="28 out of 28 forms covered">
071&nbsp;&nbsp;&nbsp;&nbsp;(and&nbsp;(&gt;=&nbsp;x&nbsp;0)&nbsp;(&gt;=&nbsp;y&nbsp;0)&nbsp;(&lt;&nbsp;y&nbsp;(count&nbsp;world))&nbsp;(&lt;&nbsp;x&nbsp;(count&nbsp;(first&nbsp;world)))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
072&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
073&nbsp;&nbsp;(defn&nbsp;map-world-n-n
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
074&nbsp;&nbsp;&nbsp;&nbsp;&quot;Wholly&nbsp;non-parallel&nbsp;map&nbsp;world&nbsp;implementation;&nbsp;see&nbsp;documentation&nbsp;for&nbsp;`map-world`.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
075&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;function]
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
076&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map-world-n-n&nbsp;world&nbsp;function&nbsp;nil))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
077&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;function&nbsp;additional-args]
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
078&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(into&nbsp;[]
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
079&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map&nbsp;(fn&nbsp;[row]
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
080&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(into&nbsp;[]&nbsp;(map
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
081&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;#(apply&nbsp;function
</span><br/>
<span class="not-covered" title="0 out of 7 forms covered">
082&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cons&nbsp;world&nbsp;(cons&nbsp;%&nbsp;additional-args)))
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
083&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;row)))
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
084&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;world))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
085&nbsp;&nbsp;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
086&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
087&nbsp;&nbsp;(defn&nbsp;map-world-p-p
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
088&nbsp;&nbsp;&nbsp;&nbsp;&quot;Wholly&nbsp;parallel&nbsp;map-world&nbsp;implementation;&nbsp;see&nbsp;documentation&nbsp;for&nbsp;`map-world`.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
089&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;function]
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
090&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map-world-p-p&nbsp;world&nbsp;function&nbsp;nil))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
091&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;function&nbsp;additional-args]
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
092&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(into&nbsp;[]
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
093&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(pmap&nbsp;(fn&nbsp;[row]
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
094&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(into&nbsp;[]&nbsp;(pmap
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
095&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;#(apply&nbsp;function
</span><br/>
<span class="not-covered" title="0 out of 7 forms covered">
096&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cons&nbsp;world&nbsp;(cons&nbsp;%&nbsp;additional-args)))
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
097&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;row)))
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
098&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;world))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
099&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
100&nbsp;&nbsp;(defn&nbsp;map-world
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
101&nbsp;&nbsp;&nbsp;&nbsp;&quot;Apply&nbsp;this&nbsp;`function`&nbsp;to&nbsp;each&nbsp;cell&nbsp;in&nbsp;this&nbsp;`world`&nbsp;to&nbsp;produce&nbsp;a&nbsp;new&nbsp;world.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
102&nbsp;&nbsp;&nbsp;&nbsp;the&nbsp;arguments&nbsp;to&nbsp;the&nbsp;function&nbsp;will&nbsp;be&nbsp;the&nbsp;world,&nbsp;the&nbsp;cell,&nbsp;and&nbsp;any
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
103&nbsp;&nbsp;&nbsp;&nbsp;`additional-args`&nbsp;supplied.&nbsp;Note&nbsp;that&nbsp;we&nbsp;parallel&nbsp;map&nbsp;over&nbsp;rows&nbsp;but
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
104&nbsp;&nbsp;&nbsp;&nbsp;just&nbsp;map&nbsp;over&nbsp;cells&nbsp;within&nbsp;a&nbsp;row.&nbsp;That&#x27;s&nbsp;because&nbsp;it&nbsp;isn&#x27;t&nbsp;worth&nbsp;starting
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
105&nbsp;&nbsp;&nbsp;&nbsp;a&nbsp;new&nbsp;thread&nbsp;for&nbsp;each&nbsp;cell,&nbsp;but&nbsp;there&nbsp;may&nbsp;be&nbsp;efficiency&nbsp;gains&nbsp;in
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
106&nbsp;&nbsp;&nbsp;&nbsp;running&nbsp;rows&nbsp;in&nbsp;parallel.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
107&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;function]
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
108&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map-world&nbsp;world&nbsp;function&nbsp;nil))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
109&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;function&nbsp;additional-args]
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
110&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(into&nbsp;[]
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
111&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(pmap&nbsp;(fn&nbsp;[row]
</span><br/>
<span class="covered" title="6 out of 6 forms covered">
112&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(into&nbsp;[]&nbsp;(map
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
113&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;#(apply&nbsp;function
</span><br/>
<span class="covered" title="7 out of 7 forms covered">
114&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cons&nbsp;world&nbsp;(cons&nbsp;%&nbsp;additional-args)))
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
115&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;row)))
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
116&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;world))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
117&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
118&nbsp;&nbsp;(defn&nbsp;get-cell
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
119&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;the&nbsp;cell&nbsp;a&nbsp;x,&nbsp;y&nbsp;in&nbsp;this&nbsp;world,&nbsp;if&nbsp;any.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
120&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
121&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;a&nbsp;world&nbsp;as&nbsp;defined&nbsp;in&nbsp;[world.clj](mw-engine.world.html);
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
122&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`x`&nbsp;a&nbsp;number&nbsp;which&nbsp;may&nbsp;or&nbsp;may&nbsp;not&nbsp;be&nbsp;a&nbsp;valid&nbsp;x&nbsp;coordinate&nbsp;within&nbsp;that&nbsp;world;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
123&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`y`&nbsp;a&nbsp;number&nbsp;which&nbsp;may&nbsp;or&nbsp;may&nbsp;not&nbsp;be&nbsp;a&nbsp;valid&nbsp;y&nbsp;coordinate&nbsp;within&nbsp;that&nbsp;world.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
124&nbsp;&nbsp;&nbsp;&nbsp;[world&nbsp;x&nbsp;y]
</span><br/>
<span class="covered" title="7 out of 7 forms covered">
125&nbsp;&nbsp;&nbsp;&nbsp;(when&nbsp;(in-bounds?&nbsp;world&nbsp;x&nbsp;y)
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
126&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(nth&nbsp;(nth&nbsp;world&nbsp;y)&nbsp;x)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
127&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
128&nbsp;&nbsp;(defn&nbsp;get-int
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
129&nbsp;&nbsp;&nbsp;&nbsp;&quot;Get&nbsp;the&nbsp;value&nbsp;of&nbsp;a&nbsp;property&nbsp;expected&nbsp;to&nbsp;be&nbsp;an&nbsp;integer&nbsp;from&nbsp;a&nbsp;map;&nbsp;if&nbsp;not
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
130&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;present&nbsp;(or&nbsp;not&nbsp;an&nbsp;integer)&nbsp;return&nbsp;0.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
131&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
132&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`map`&nbsp;a&nbsp;map;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
133&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`key`&nbsp;a&nbsp;symbol&nbsp;or&nbsp;keyword,&nbsp;presumed&nbsp;to&nbsp;be&nbsp;a&nbsp;key&nbsp;into&nbsp;the&nbsp;`map`.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
134&nbsp;&nbsp;&nbsp;&nbsp;[map&nbsp;key]
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
135&nbsp;&nbsp;&nbsp;&nbsp;(if&nbsp;(map?&nbsp;map)
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
136&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[v&nbsp;(map&nbsp;key)]
</span><br/>
<span class="covered" title="12 out of 12 forms covered">
137&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(and&nbsp;v&nbsp;(integer?&nbsp;v))&nbsp;v
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
138&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:else&nbsp;0))
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
139&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(throw&nbsp;(Exception.&nbsp;&quot;No&nbsp;map&nbsp;passed?&quot;))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
140&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
141&nbsp;&nbsp;(defn&nbsp;get-num
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
142&nbsp;&nbsp;&nbsp;&nbsp;&quot;Get&nbsp;the&nbsp;value&nbsp;of&nbsp;a&nbsp;property&nbsp;expected&nbsp;to&nbsp;be&nbsp;a&nbsp;number&nbsp;from&nbsp;a&nbsp;map;&nbsp;if&nbsp;not
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
143&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;present&nbsp;(or&nbsp;not&nbsp;a&nbsp;number)&nbsp;return&nbsp;0.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
144&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
145&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`map`&nbsp;a&nbsp;map;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
146&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`key`&nbsp;a&nbsp;symbol&nbsp;or&nbsp;keyword,&nbsp;presumed&nbsp;to&nbsp;be&nbsp;a&nbsp;key&nbsp;into&nbsp;the&nbsp;`map`.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
147&nbsp;&nbsp;&nbsp;&nbsp;[map&nbsp;key]
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
148&nbsp;&nbsp;&nbsp;&nbsp;(if&nbsp;(map?&nbsp;map)
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
149&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[v&nbsp;(map&nbsp;key)]
</span><br/>
<span class="covered" title="12 out of 12 forms covered">
150&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(and&nbsp;v&nbsp;(number?&nbsp;v))&nbsp;v
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
151&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:else&nbsp;0))
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
152&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(throw&nbsp;(Exception.&nbsp;&quot;No&nbsp;map&nbsp;passed?&quot;))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
153&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
154&nbsp;&nbsp;(defn&nbsp;population
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
155&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;the&nbsp;population&nbsp;of&nbsp;this&nbsp;species&nbsp;in&nbsp;this&nbsp;cell.&nbsp;Currently&nbsp;a&nbsp;synonym&nbsp;for
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
156&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;`get-int`,&nbsp;but&nbsp;may&nbsp;not&nbsp;always&nbsp;be&nbsp;(depending&nbsp;whether&nbsp;species&nbsp;are&nbsp;later
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
157&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;implemented&nbsp;as&nbsp;actors)
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
158&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
159&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`cell`&nbsp;a&nbsp;map;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
160&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`species`&nbsp;a&nbsp;keyword&nbsp;representing&nbsp;a&nbsp;species&nbsp;which&nbsp;may&nbsp;populate&nbsp;that&nbsp;cell.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
161&nbsp;&nbsp;&nbsp;&nbsp;[cell&nbsp;species]
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
162&nbsp;&nbsp;&nbsp;&nbsp;(get-int&nbsp;cell&nbsp;species))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
163&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
164&nbsp;&nbsp;(def&nbsp;memo-get-neighbours
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
165&nbsp;&nbsp;&nbsp;&nbsp;&quot;Memoised&nbsp;get&nbsp;neighbours&nbsp;is&nbsp;more&nbsp;efficient&nbsp;when&nbsp;running&nbsp;deeply&nbsp;recursive
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
166&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;algorithms&nbsp;on&nbsp;the&nbsp;same&nbsp;world.&nbsp;But&nbsp;it&#x27;s&nbsp;less&nbsp;efficient&nbsp;when&nbsp;running&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
167&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;engine&nbsp;in&nbsp;its&nbsp;normal&nbsp;iterative&nbsp;style,&nbsp;because&nbsp;then&nbsp;we&nbsp;will&nbsp;rarely&nbsp;call
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
168&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;get&nbsp;naighbours&nbsp;on&nbsp;the&nbsp;same&nbsp;cell&nbsp;of&nbsp;the&nbsp;same&nbsp;world&nbsp;twice.&quot;
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
169&nbsp;&nbsp;&nbsp;&nbsp;(memoize
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
170&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[world&nbsp;x&nbsp;y&nbsp;depth]
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
171&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(remove&nbsp;nil?
</span><br/>
<span class="covered" title="14 out of 14 forms covered">
172&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map&nbsp;#(get-cell&nbsp;world&nbsp;(first&nbsp;%)&nbsp;(first&nbsp;(rest&nbsp;%)))
</span><br/>
<span class="covered" title="9 out of 9 forms covered">
173&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(remove&nbsp;#(=&nbsp;%&nbsp;(list&nbsp;x&nbsp;y))
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
174&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(combo&#x2F;cartesian-product
</span><br/>
<span class="covered" title="10 out of 10 forms covered">
175&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(range&nbsp;(-&nbsp;x&nbsp;depth)&nbsp;(+&nbsp;x&nbsp;depth&nbsp;1))
</span><br/>
<span class="covered" title="10 out of 10 forms covered">
176&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(range&nbsp;(-&nbsp;y&nbsp;depth)&nbsp;(+&nbsp;y&nbsp;depth&nbsp;1)))))))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
177&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
178&nbsp;&nbsp;(defn&nbsp;get-neighbours
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
179&nbsp;&nbsp;&nbsp;&nbsp;&quot;Get&nbsp;the&nbsp;neighbours&nbsp;to&nbsp;distance&nbsp;depth&nbsp;of&nbsp;a&nbsp;cell&nbsp;in&nbsp;this&nbsp;world.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
180&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
181&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Several&nbsp;overloads:
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
182&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;a&nbsp;world,&nbsp;as&nbsp;described&nbsp;in&nbsp;[world.clj](mw-engine.world.html);
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
183&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`cell`&nbsp;a&nbsp;cell&nbsp;within&nbsp;that&nbsp;world
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
184&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Gets&nbsp;immediate&nbsp;neighbours&nbsp;of&nbsp;the&nbsp;specified&nbsp;cell.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
185&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
186&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;a&nbsp;world,&nbsp;as&nbsp;described&nbsp;in[world.clj](mw-engine.world.html);
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
187&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`cell`&nbsp;a&nbsp;cell&nbsp;within&nbsp;that&nbsp;world
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
188&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`depth`&nbsp;an&nbsp;integer&nbsp;representing&nbsp;the&nbsp;depth&nbsp;to&nbsp;search&nbsp;from&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
189&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;`cell`
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
190&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Gets&nbsp;neighbours&nbsp;within&nbsp;the&nbsp;specified&nbsp;distance&nbsp;of&nbsp;the&nbsp;cell.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
191&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
192&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;a&nbsp;world,&nbsp;as&nbsp;described&nbsp;in[world.clj](mw-engine.world.html);
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
193&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`x`&nbsp;an&nbsp;integer&nbsp;representing&nbsp;an&nbsp;x&nbsp;coordinate&nbsp;in&nbsp;that&nbsp;world;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
194&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`y`&nbsp;an&nbsp;integer&nbsp;representing&nbsp;an&nbsp;y&nbsp;coordinate&nbsp;in&nbsp;that&nbsp;world;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
195&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`depth`&nbsp;an&nbsp;integer&nbsp;representing&nbsp;the&nbsp;distance&nbsp;from&nbsp;[x,y]&nbsp;that
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
196&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;should&nbsp;be&nbsp;searched
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
197&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Gets&nbsp;the&nbsp;neighbours&nbsp;within&nbsp;the&nbsp;specified&nbsp;distance&nbsp;of&nbsp;the&nbsp;cell&nbsp;at
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
198&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;coordinates&nbsp;[x,y]&nbsp;in&nbsp;this&nbsp;world.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
199&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;x&nbsp;y&nbsp;depth]
</span><br/>
<span class="covered" title="6 out of 6 forms covered">
200&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(memo-get-neighbours&nbsp;world&nbsp;x&nbsp;y&nbsp;depth))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
201&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;cell&nbsp;depth]
</span><br/>
<span class="covered" title="10 out of 10 forms covered">
202&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(memo-get-neighbours&nbsp;world&nbsp;(:x&nbsp;cell)&nbsp;(:y&nbsp;cell)&nbsp;depth))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
203&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;cell]
</span><br/>
<span class="covered" title="10 out of 10 forms covered">
204&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(memo-get-neighbours&nbsp;world&nbsp;(:x&nbsp;cell)&nbsp;(:y&nbsp;cell)&nbsp;1)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
205&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
206&nbsp;&nbsp;(defn&nbsp;get-neighbours-with-property-value
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
207&nbsp;&nbsp;&nbsp;&nbsp;&quot;Get&nbsp;the&nbsp;neighbours&nbsp;to&nbsp;distance&nbsp;depth&nbsp;of&nbsp;the&nbsp;cell&nbsp;at&nbsp;x,&nbsp;y&nbsp;in&nbsp;this&nbsp;world&nbsp;which
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
208&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;have&nbsp;this&nbsp;value&nbsp;for&nbsp;this&nbsp;property.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
209&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
210&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;a&nbsp;world,&nbsp;as&nbsp;described&nbsp;in&nbsp;[world.clj](mw-engine.world.html);
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
211&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`cell`&nbsp;a&nbsp;cell&nbsp;within&nbsp;that&nbsp;world;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
212&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`depth`&nbsp;an&nbsp;integer&nbsp;representing&nbsp;the&nbsp;distance&nbsp;from&nbsp;[x,y]&nbsp;that
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
213&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;should&nbsp;be&nbsp;searched&nbsp;(optional);
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
214&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`property`&nbsp;a&nbsp;keyword&nbsp;representing&nbsp;a&nbsp;property&nbsp;of&nbsp;the&nbsp;neighbours;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
215&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`value`&nbsp;a&nbsp;value&nbsp;of&nbsp;that&nbsp;property&nbsp;(or,&nbsp;possibly,&nbsp;the&nbsp;name&nbsp;of&nbsp;another);
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
216&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`op`&nbsp;a&nbsp;comparator&nbsp;function&nbsp;to&nbsp;use&nbsp;in&nbsp;place&nbsp;of&nbsp;`=`&nbsp;(optional).
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
217&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
218&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;It&nbsp;gets&nbsp;messy.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
219&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;x&nbsp;y&nbsp;depth&nbsp;property&nbsp;value&nbsp;op]
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
220&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(filter
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
221&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;#(eval
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
222&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(list&nbsp;op
</span><br/>
<span class="covered" title="11 out of 11 forms covered">
223&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(or&nbsp;(get&nbsp;%&nbsp;property)&nbsp;(get-int&nbsp;%&nbsp;property))
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
224&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;value))
</span><br/>
<span class="covered" title="6 out of 6 forms covered">
225&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-neighbours&nbsp;world&nbsp;x&nbsp;y&nbsp;depth)))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
226&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;x&nbsp;y&nbsp;depth&nbsp;property&nbsp;value]
</span><br/>
<span class="covered" title="9 out of 9 forms covered">
227&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-neighbours-with-property-value&nbsp;world&nbsp;x&nbsp;y&nbsp;depth&nbsp;property&nbsp;value&nbsp;=))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
228&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;cell&nbsp;depth&nbsp;property&nbsp;value]
</span><br/>
<span class="not-covered" title="0 out of 10 forms covered">
229&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-neighbours-with-property-value&nbsp;world&nbsp;(:x&nbsp;cell)&nbsp;(:y&nbsp;cell)&nbsp;depth
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
230&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;property&nbsp;value))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
231&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;cell&nbsp;property&nbsp;value]
</span><br/>
<span class="not-covered" title="0 out of 5 forms covered">
232&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-neighbours-with-property-value&nbsp;world&nbsp;cell&nbsp;1
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
233&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;property&nbsp;value)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
234&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
235&nbsp;&nbsp;(defn&nbsp;get-neighbours-with-state
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
236&nbsp;&nbsp;&nbsp;&nbsp;&quot;Get&nbsp;the&nbsp;neighbours&nbsp;to&nbsp;distance&nbsp;depth&nbsp;of&nbsp;the&nbsp;cell&nbsp;at&nbsp;x,&nbsp;y&nbsp;in&nbsp;this&nbsp;world&nbsp;which
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
237&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;have&nbsp;this&nbsp;state.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
238&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
239&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;a&nbsp;world,&nbsp;as&nbsp;described&nbsp;in&nbsp;[world.clj](mw-engine.world.html);
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
240&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`cell`&nbsp;a&nbsp;cell&nbsp;within&nbsp;that&nbsp;world;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
241&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`depth`&nbsp;an&nbsp;integer&nbsp;representing&nbsp;the&nbsp;distance&nbsp;from&nbsp;[x,y]&nbsp;that
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
242&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;should&nbsp;be&nbsp;searched;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
243&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`state`&nbsp;a&nbsp;keyword&nbsp;representing&nbsp;a&nbsp;state&nbsp;in&nbsp;the&nbsp;world.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
244&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;x&nbsp;y&nbsp;depth&nbsp;state]
</span><br/>
<span class="not-covered" title="0 out of 14 forms covered">
245&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(filter&nbsp;#(=&nbsp;(:state&nbsp;%)&nbsp;state)&nbsp;(get-neighbours&nbsp;world&nbsp;x&nbsp;y&nbsp;depth)))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
246&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;cell&nbsp;depth&nbsp;state]
</span><br/>
<span class="not-covered" title="0 out of 11 forms covered">
247&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-neighbours-with-state&nbsp;world&nbsp;(:x&nbsp;cell)&nbsp;(:y&nbsp;cell)&nbsp;depth&nbsp;state))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
248&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;cell&nbsp;state]
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
249&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(get-neighbours-with-state&nbsp;world&nbsp;cell&nbsp;1&nbsp;state)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
250&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
251&nbsp;&nbsp;(defn&nbsp;get-least-cell
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
252&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;the&nbsp;cell&nbsp;from&nbsp;among&nbsp;these&nbsp;`cells`&nbsp;which&nbsp;has&nbsp;the&nbsp;lowest&nbsp;numeric&nbsp;value
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
253&nbsp;&nbsp;&nbsp;&nbsp;for&nbsp;this&nbsp;`property`.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
254&nbsp;&nbsp;&nbsp;&nbsp;[cells&nbsp;property]
</span><br/>
<span class="covered" title="14 out of 14 forms covered">
255&nbsp;&nbsp;&nbsp;&nbsp;(first&nbsp;(sort-by&nbsp;property&nbsp;(filter&nbsp;#(number?&nbsp;(property&nbsp;%))&nbsp;cells))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
256&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
257&nbsp;&nbsp;(defn&nbsp;get-most-cell
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
258&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;the&nbsp;cell&nbsp;from&nbsp;among&nbsp;these&nbsp;`cells`&nbsp;which&nbsp;has&nbsp;the&nbsp;highest&nbsp;numeric&nbsp;value
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
259&nbsp;&nbsp;&nbsp;&nbsp;for&nbsp;this&nbsp;`property`.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
260&nbsp;&nbsp;&nbsp;&nbsp;[cells&nbsp;property]
</span><br/>
<span class="covered" title="14 out of 14 forms covered">
261&nbsp;&nbsp;&nbsp;&nbsp;(last&nbsp;(sort-by&nbsp;property&nbsp;(filter&nbsp;#(number?&nbsp;(property&nbsp;%))&nbsp;cells))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
262&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
263&nbsp;&nbsp;(defn-&nbsp;set-cell-property
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
264&nbsp;&nbsp;&nbsp;&nbsp;&quot;If&nbsp;this&nbsp;`cell`s&nbsp;x&nbsp;and&nbsp;y&nbsp;properties&nbsp;are&nbsp;equal&nbsp;to&nbsp;these&nbsp;`x`&nbsp;and&nbsp;`y`&nbsp;values,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
265&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return&nbsp;a&nbsp;cell&nbsp;like&nbsp;this&nbsp;cell&nbsp;but&nbsp;with&nbsp;the&nbsp;value&nbsp;of&nbsp;this&nbsp;`property`&nbsp;set&nbsp;to
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
266&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;this&nbsp;`value`.&nbsp;Otherwise,&nbsp;just&nbsp;return&nbsp;this&nbsp;`cell`.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
267&nbsp;&nbsp;&nbsp;&nbsp;[cell&nbsp;x&nbsp;y&nbsp;property&nbsp;value]
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
268&nbsp;&nbsp;&nbsp;&nbsp;(cond
</span><br/>
<span class="covered" title="14 out of 14 forms covered">
269&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(and&nbsp;(=&nbsp;x&nbsp;(:x&nbsp;cell))&nbsp;(=&nbsp;y&nbsp;(:y&nbsp;cell)))
</span><br/>
<span class="covered" title="8 out of 8 forms covered">
270&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;cell&nbsp;{property&nbsp;value&nbsp;:rule&nbsp;&quot;Set&nbsp;by&nbsp;user&quot;})
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
271&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:else&nbsp;cell))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
272&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
273&nbsp;&nbsp;(defn&nbsp;set-property
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
274&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;a&nbsp;world&nbsp;like&nbsp;this&nbsp;`world`&nbsp;but&nbsp;with&nbsp;the&nbsp;value&nbsp;of&nbsp;exactly&nbsp;one&nbsp;`property`
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
275&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;of&nbsp;one&nbsp;`cell`&nbsp;changed&nbsp;to&nbsp;this&nbsp;`value`&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
276&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;cell&nbsp;property&nbsp;value]
</span><br/>
<span class="covered" title="11 out of 11 forms covered">
277&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(set-property&nbsp;world&nbsp;(:x&nbsp;cell)&nbsp;(:y&nbsp;cell)&nbsp;property&nbsp;value))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
278&nbsp;&nbsp;&nbsp;&nbsp;([world&nbsp;x&nbsp;y&nbsp;property&nbsp;value]
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
279&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(apply
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
280&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;vector&nbsp;;;&nbsp;we&nbsp;want&nbsp;a&nbsp;vector&nbsp;of&nbsp;vectors,&nbsp;not&nbsp;a&nbsp;list&nbsp;of&nbsp;lists,&nbsp;for&nbsp;efficiency
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
281&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
282&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(fn&nbsp;[row]
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
283&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(apply
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
284&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;vector
</span><br/>
<span class="covered" title="10 out of 10 forms covered">
285&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map&nbsp;#(set-cell-property&nbsp;%&nbsp;x&nbsp;y&nbsp;property&nbsp;value)
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
286&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;row)))
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
287&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;world))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
288&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
289&nbsp;&nbsp;(defn&nbsp;merge-cell
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
290&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;a&nbsp;world&nbsp;like&nbsp;this&nbsp;`world`,&nbsp;but&nbsp;merge&nbsp;the&nbsp;values&nbsp;from&nbsp;this&nbsp;`cell`&nbsp;with
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
291&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;those&nbsp;from&nbsp;the&nbsp;cell&nbsp;in&nbsp;the&nbsp;world&nbsp;with&nbsp;the&nbsp;same&nbsp;co-ordinates&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
292&nbsp;&nbsp;&nbsp;&nbsp;[world&nbsp;cell]
</span><br/>
<span class="covered" title="10 out of 10 forms covered">
293&nbsp;&nbsp;&nbsp;&nbsp;(if&nbsp;(in-bounds?&nbsp;world&nbsp;(:x&nbsp;cell)&nbsp;(:y&nbsp;cell))
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
294&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map-world&nbsp;world
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
295&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;#(if
</span><br/>
<span class="covered" title="5 out of 5 forms covered">
296&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(and
</span><br/>
<span class="covered" title="7 out of 7 forms covered">
297&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(=&nbsp;(:x&nbsp;cell)&nbsp;(:x&nbsp;%2))
</span><br/>
<span class="covered" title="6 out of 6 forms covered">
298&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(=&nbsp;(:y&nbsp;cell)&nbsp;(:y&nbsp;%2)))
</span><br/>
<span class="covered" title="4 out of 4 forms covered">
299&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(merge&nbsp;%2&nbsp;cell)
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
300&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;%2))
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
301&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;world))
</span><br/>
</body>
</html>

View file

@ -0,0 +1,275 @@
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<link rel="stylesheet" href="../coverage.css"/> <title> mw_engine/world.clj </title>
</head>
<body>
<span class="covered" title="1 out of 1 forms covered">
001&nbsp;&nbsp;(ns&nbsp;^{:doc&nbsp;&quot;Functions&nbsp;to&nbsp;create&nbsp;and&nbsp;to&nbsp;print&nbsp;two&nbsp;dimensional&nbsp;cellular&nbsp;automata.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
002&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
003&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Nothing&nbsp;in&nbsp;this&nbsp;namespace&nbsp;should&nbsp;determine&nbsp;what&nbsp;states&nbsp;are&nbsp;possible&nbsp;within
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
004&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;the&nbsp;automaton,&nbsp;except&nbsp;for&nbsp;the&nbsp;initial&nbsp;state,&nbsp;:new.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
005&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
006&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;A&nbsp;cell&nbsp;is&nbsp;a&nbsp;map&nbsp;containing&nbsp;at&nbsp;least&nbsp;values&nbsp;for&nbsp;the&nbsp;keys&nbsp;`:x`,&nbsp;`:y`,&nbsp;and&nbsp;`:state`.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
007&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
008&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;A&nbsp;world&nbsp;is&nbsp;a&nbsp;two&nbsp;dimensional&nbsp;matrix&nbsp;(sequence&nbsp;of&nbsp;sequences)&nbsp;of&nbsp;cells,&nbsp;such
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
009&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;that&nbsp;every&nbsp;cell&#x27;s&nbsp;`:x`&nbsp;and&nbsp;`:y`&nbsp;properties&nbsp;reflect&nbsp;its&nbsp;place&nbsp;in&nbsp;the&nbsp;matrix.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
010&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:author&nbsp;&quot;Simon&nbsp;Brooke&quot;}
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
011&nbsp;&nbsp;&nbsp;mw-engine.world
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
012&nbsp;&nbsp;&nbsp;&nbsp;(:require&nbsp;[clojure.string&nbsp;:as&nbsp;string]
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
013&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[mw-engine.utils&nbsp;:refer&nbsp;[population]]))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
014&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
015&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
016&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
017&nbsp;&nbsp;;;;;&nbsp;mw-engine:&nbsp;the&nbsp;state&#x2F;transition&nbsp;engine&nbsp;of&nbsp;MicroWorld.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
018&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
019&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;free&nbsp;software;&nbsp;you&nbsp;can&nbsp;redistribute&nbsp;it&nbsp;and&#x2F;or
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
020&nbsp;&nbsp;;;;;&nbsp;modify&nbsp;it&nbsp;under&nbsp;the&nbsp;terms&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
021&nbsp;&nbsp;;;;;&nbsp;as&nbsp;published&nbsp;by&nbsp;the&nbsp;Free&nbsp;Software&nbsp;Foundation;&nbsp;either&nbsp;version&nbsp;2
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
022&nbsp;&nbsp;;;;;&nbsp;of&nbsp;the&nbsp;License,&nbsp;or&nbsp;(at&nbsp;your&nbsp;option)&nbsp;any&nbsp;later&nbsp;version.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
023&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
024&nbsp;&nbsp;;;;;&nbsp;This&nbsp;program&nbsp;is&nbsp;distributed&nbsp;in&nbsp;the&nbsp;hope&nbsp;that&nbsp;it&nbsp;will&nbsp;be&nbsp;useful,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
025&nbsp;&nbsp;;;;;&nbsp;but&nbsp;WITHOUT&nbsp;ANY&nbsp;WARRANTY;&nbsp;without&nbsp;even&nbsp;the&nbsp;implied&nbsp;warranty&nbsp;of
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
026&nbsp;&nbsp;;;;;&nbsp;MERCHANTABILITY&nbsp;or&nbsp;FITNESS&nbsp;FOR&nbsp;A&nbsp;PARTICULAR&nbsp;PURPOSE.&nbsp;&nbsp;See&nbsp;the
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
027&nbsp;&nbsp;;;;;&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License&nbsp;for&nbsp;more&nbsp;details.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
028&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
029&nbsp;&nbsp;;;;;&nbsp;You&nbsp;should&nbsp;have&nbsp;received&nbsp;a&nbsp;copy&nbsp;of&nbsp;the&nbsp;GNU&nbsp;General&nbsp;Public&nbsp;License
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
030&nbsp;&nbsp;;;;;&nbsp;along&nbsp;with&nbsp;this&nbsp;program;&nbsp;if&nbsp;not,&nbsp;write&nbsp;to&nbsp;the&nbsp;Free&nbsp;Software
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
031&nbsp;&nbsp;;;;;&nbsp;Foundation,&nbsp;Inc.,&nbsp;51&nbsp;Franklin&nbsp;Street,&nbsp;Fifth&nbsp;Floor,&nbsp;Boston,&nbsp;MA&nbsp;&nbsp;02110-1301,
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
032&nbsp;&nbsp;;;;;&nbsp;USA.
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
033&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
034&nbsp;&nbsp;;;;;&nbsp;Copyright&nbsp;(C)&nbsp;2014&nbsp;Simon&nbsp;Brooke
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
035&nbsp;&nbsp;;;;;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
036&nbsp;&nbsp;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
037&nbsp;&nbsp;
</span><br/>
<span class="covered" title="30 out of 30 forms covered">
038&nbsp;&nbsp;(defmacro&nbsp;make-cell
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
039&nbsp;&nbsp;&nbsp;&nbsp;&quot;Create&nbsp;a&nbsp;minimal&nbsp;default&nbsp;cell&nbsp;at&nbsp;x,&nbsp;y
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
040&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
041&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`x`&nbsp;the&nbsp;x&nbsp;coordinate&nbsp;at&nbsp;which&nbsp;this&nbsp;cell&nbsp;is&nbsp;created;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
042&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`y`&nbsp;the&nbsp;y&nbsp;coordinate&nbsp;at&nbsp;which&nbsp;this&nbsp;cell&nbsp;is&nbsp;created.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
043&nbsp;&nbsp;&nbsp;&nbsp;[x&nbsp;y]
</span><br/>
<span class="covered" title="2 out of 2 forms covered">
044&nbsp;&nbsp;&nbsp;&nbsp;`{:x&nbsp;~x&nbsp;:y&nbsp;~y&nbsp;:state&nbsp;:new})
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
045&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
046&nbsp;&nbsp;(defn&nbsp;make-world
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
047&nbsp;&nbsp;&nbsp;&nbsp;&quot;Make&nbsp;a&nbsp;world&nbsp;width&nbsp;cells&nbsp;from&nbsp;east&nbsp;to&nbsp;west,&nbsp;and&nbsp;height&nbsp;cells&nbsp;from&nbsp;north&nbsp;to
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
048&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;south.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
049&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
050&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`width`&nbsp;a&nbsp;natural&nbsp;number&nbsp;representing&nbsp;the&nbsp;width&nbsp;of&nbsp;the&nbsp;matrix&nbsp;to&nbsp;be&nbsp;created;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
051&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`height`&nbsp;a&nbsp;natural&nbsp;number&nbsp;representing&nbsp;the&nbsp;height&nbsp;of&nbsp;the&nbsp;matrix&nbsp;to&nbsp;be&nbsp;created.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
052&nbsp;&nbsp;&nbsp;&nbsp;[width&nbsp;height]
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
053&nbsp;&nbsp;&nbsp;&nbsp;(apply&nbsp;vector
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
054&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map&nbsp;(fn&nbsp;[h]
</span><br/>
<span class="covered" title="16 out of 16 forms covered">
055&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(apply&nbsp;vector&nbsp;(map&nbsp;#(make-cell&nbsp;%&nbsp;h)&nbsp;(range&nbsp;width))))
</span><br/>
<span class="covered" title="3 out of 3 forms covered">
056&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(range&nbsp;height))))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
057&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
058&nbsp;&nbsp;(defn&nbsp;truncate-state
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
059&nbsp;&nbsp;&nbsp;&nbsp;&quot;Truncate&nbsp;the&nbsp;print&nbsp;name&nbsp;of&nbsp;the&nbsp;state&nbsp;of&nbsp;this&nbsp;cell&nbsp;to&nbsp;at&nbsp;most&nbsp;limit&nbsp;characters.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
060&nbsp;&nbsp;&nbsp;&nbsp;[cell&nbsp;limit]
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
061&nbsp;&nbsp;&nbsp;&nbsp;(let&nbsp;[s&nbsp;(:state&nbsp;cell)]
</span><br/>
<span class="not-covered" title="0 out of 13 forms covered">
062&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(cond&nbsp;(&gt;&nbsp;(count&nbsp;(str&nbsp;s))&nbsp;limit)&nbsp;(subs&nbsp;s&nbsp;0&nbsp;limit)
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
063&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;:else&nbsp;s)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
064&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
065&nbsp;&nbsp;(defn&nbsp;format-cell
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
066&nbsp;&nbsp;&nbsp;&nbsp;&quot;Return&nbsp;a&nbsp;formatted&nbsp;string&nbsp;summarising&nbsp;the&nbsp;current&nbsp;state&nbsp;of&nbsp;this&nbsp;cell.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
067&nbsp;&nbsp;&nbsp;&nbsp;[cell]
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
068&nbsp;&nbsp;&nbsp;&nbsp;(format&nbsp;&quot;%10s(%2d&#x2F;%2d)&quot;
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
069&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(truncate-state&nbsp;cell&nbsp;10)
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
070&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(population&nbsp;cell&nbsp;:deer)
</span><br/>
<span class="not-covered" title="0 out of 4 forms covered">
071&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(population&nbsp;cell&nbsp;:wolves)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
072&nbsp;&nbsp;
</span><br/>
<span class="covered" title="1 out of 1 forms covered">
073&nbsp;&nbsp;(defn-&nbsp;format-world-row
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
074&nbsp;&nbsp;&nbsp;&nbsp;&quot;Format&nbsp;one&nbsp;row&nbsp;in&nbsp;the&nbsp;state&nbsp;of&nbsp;a&nbsp;world&nbsp;for&nbsp;printing.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
075&nbsp;&nbsp;&nbsp;&nbsp;[row]
</span><br/>
<span class="not-covered" title="0 out of 6 forms covered">
076&nbsp;&nbsp;&nbsp;&nbsp;(string&#x2F;join&nbsp;(map&nbsp;format-cell&nbsp;row)))
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
077&nbsp;&nbsp;
</span><br/>
<span class="partial" title="1 out of 2 forms covered">
078&nbsp;&nbsp;(defn&nbsp;print-world
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
079&nbsp;&nbsp;&nbsp;&nbsp;&quot;Print&nbsp;the&nbsp;current&nbsp;state&nbsp;of&nbsp;this&nbsp;world,&nbsp;and&nbsp;return&nbsp;nil.
</span><br/>
<span class="blank" title="0 out of 0 forms covered">
080&nbsp;&nbsp;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
081&nbsp;&nbsp;&nbsp;&nbsp;*&nbsp;`world`&nbsp;a&nbsp;world&nbsp;as&nbsp;defined&nbsp;above.&quot;
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
082&nbsp;&nbsp;&nbsp;&nbsp;[world]
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
083&nbsp;&nbsp;&nbsp;&nbsp;(println)
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
084&nbsp;&nbsp;&nbsp;&nbsp;(dorun
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
085&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(map
</span><br/>
<span class="not-covered" title="0 out of 2 forms covered">
086&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;#(println
</span><br/>
<span class="not-covered" title="0 out of 3 forms covered">
087&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(format-world-row&nbsp;%))
</span><br/>
<span class="not-covered" title="0 out of 1 forms covered">
088&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;world))
</span><br/>
<span class="not-tracked" title="0 out of 0 forms covered">
089&nbsp;&nbsp;&nbsp;&nbsp;nil)
</span><br/>
</body>
</html>