|
@@ -32,14 +32,19 @@ def eval_prog(args):
|
32
|
32
|
turmit()
|
33
|
33
|
stop = time.time()
|
34
|
34
|
|
35
|
|
- score = w.fractdim()
|
|
35
|
+ score_dir = sum([t.dirvar() for t in turmits]) / len(turmits)
|
|
36
|
+ score_fract = w.fractdim()
|
|
37
|
+ score = score_dir * score_fract
|
|
38
|
+ sinfo = {'F':score_fract, 'D':score_dir}
|
|
39
|
+ #score = sum([score_fract] + [score_dir] * 4) / 5
|
36
|
40
|
if not args.quiet:
|
37
|
|
- msg = 'G%d P%d run#%d %d steps scores %.3f in %.2fs (%dus per step)\t%s'
|
38
|
|
- msg %= (generation, progid, trynum, steps, score, stop - start,
|
|
41
|
+ msg = 'G%d P%d run#%d %d steps scores %.3f:(D:%.3f,F:%.3f) in %.2fs (%dus per step)\t%s'
|
|
42
|
+ msg %= (generation, progid, trynum, steps, score, score_dir,
|
|
43
|
+ score_fract, stop - start,
|
39
|
44
|
((stop - start)*1000000)//steps//len(turmits),
|
40
|
45
|
str(prog))
|
41
|
46
|
logger.info(msg)
|
42
|
|
- return progid, score
|
|
47
|
+ return progid, score, sinfo
|
43
|
48
|
|
44
|
49
|
class World(object):
|
45
|
50
|
''' @brief A Turmit world. An array of dim == 2 with tuple(R,G,B) '''
|
|
@@ -192,6 +197,15 @@ class LivingTurmit(Turmit):
|
192
|
197
|
raise ValueError('Invalid Y position %d' % y)
|
193
|
198
|
self._y = y
|
194
|
199
|
|
|
200
|
+ # Direction variation addon
|
|
201
|
+ self._absx = self._absy = 0
|
|
202
|
+ self._prev_abs = (0, 0)
|
|
203
|
+ self._dirvar = 0
|
|
204
|
+ self._prev_dirvar = None
|
|
205
|
+ self._dirvar_res = 50
|
|
206
|
+ self._steps = 1
|
|
207
|
+
|
|
208
|
+
|
195
|
209
|
def __call__(self):
|
196
|
210
|
''' @brief Exec a turmit and move it '''
|
197
|
211
|
if self._world._gray:
|
|
@@ -201,6 +215,29 @@ class LivingTurmit(Turmit):
|
201
|
215
|
tdir = super().__call__(x=self._x, y=self._y, r=r, g=g, b=b)
|
202
|
216
|
self.move(tdir)
|
203
|
217
|
|
|
218
|
+ # direction variation handling
|
|
219
|
+ if self._steps % self._dirvar_res == 0:
|
|
220
|
+ dy = self._absy - self._prev_abs[0]
|
|
221
|
+ dx = self._absx - self._prev_abs[1]
|
|
222
|
+ self._prev_abs = (self._absy, self._absx)
|
|
223
|
+ if self._prev_dirvar is not None:
|
|
224
|
+ pdvar = self._prev_dirvar
|
|
225
|
+ self._dirvar += abs(pdvar[0] - dy) + abs(pdvar[1] - dx)
|
|
226
|
+ self._prev_dirvar = (dy, dx)
|
|
227
|
+
|
|
228
|
+ self._steps += 1
|
|
229
|
+
|
|
230
|
+ def dirvar(self):
|
|
231
|
+ ''' @brief Process @ref _dirvar to return a direction variation
|
|
232
|
+ score
|
|
233
|
+ @return a score in [0..2]
|
|
234
|
+ '''
|
|
235
|
+ return self._dirvar / (self._steps * 2)
|
|
236
|
+ #d = self._dirvar
|
|
237
|
+ #return sum([sum([abs(d[i][j] - d[i+1][j]) for j in (0,1)])
|
|
238
|
+ # for i in range(len(d)-1)]) / (self._steps * 2)
|
|
239
|
+
|
|
240
|
+
|
204
|
241
|
def move(self, tdir, setcol=True):
|
205
|
242
|
''' @brief Update coordinates given a direction
|
206
|
243
|
@param tdir int : One of 8 directions (integer is understanded
|
|
@@ -215,17 +252,21 @@ class LivingTurmit(Turmit):
|
215
|
252
|
tdir %= 8 if self._diag else 4
|
216
|
253
|
|
217
|
254
|
if tdir == 0 or tdir == 4 or tdir == 5:
|
|
255
|
+ self._absx += 1
|
218
|
256
|
self._x += 1
|
219
|
257
|
self._x %= self._world.width
|
220
|
258
|
elif tdir == 2 or tdir == 7 or tdir == 6:
|
|
259
|
+ self._absx -= 1
|
221
|
260
|
if self._x == 0:
|
222
|
261
|
self._x = self._world.width -1
|
223
|
262
|
else:
|
224
|
263
|
self._x -= 1
|
225
|
264
|
if tdir == 1 or tdir == 4 or tdir == 6:
|
|
265
|
+ self._absy += 1
|
226
|
266
|
self._y += 1
|
227
|
267
|
self._y %= self._world.height
|
228
|
268
|
elif tdir == 3 or tdir == 7 or tdir == 5:
|
|
269
|
+ self._absy -= 1
|
229
|
270
|
if self._y == 0:
|
230
|
271
|
self._y = self._world.height - 1
|
231
|
272
|
else:
|