Differences From Artifact [4dfcc976e17caad5]:
- File
src/solver.d
- 2012-07-15 15:42:31 - part of checkin [310a3c5d41] on branch trunk - speed testing... 100x100 no-op is fast enough... (user: kinaba) [annotate]
To Artifact [707b7344a0841f62]:
- File
src/solver.d
- 2012-07-15 16:06:29 - part of checkin [913d120d42] on branch trunk - size tuning solver (user: kinaba) [annotate]
1 1 import util;
2 2 import game;
3 3
4 4 bool rocky(char c){ return c=='*'||c=='@'; }
5 5
6 -class Solver_0
6 +interface Solver
7 +{
8 + // this(in Game g);
9 + char single_step();
10 + void force(char c);
11 +}
12 +
13 +class Solver_0 : Solver
7 14 {
8 15 this(in Game g) {}
9 16 char single_step() { return 'W'; }
10 17 void force(char c) {}
11 18 }
12 19
13 -class Solver_1
20 +class Solver_1 : Solver
14 21 {
15 22 int wait_count = 0;
16 23 int choke_count = 0;
17 24
18 25 Game g;
19 26 this(in Game g)
20 27 {
................................................................................
163 170 {
164 171 bool danger(int y, int x)
165 172 {
166 173 if(g.map[y,x] == ' ' || g.map[y,x] == 'R')
167 174 return false;
168 175 if(rocky(g.map[y+1,x]))
169 176 return true;
170 - if(rocky(g.map[y+1,x-1]) && (g.map[y,x-1]=='\\'||rocky(g.map[y,x-1])) && (g.map[y+1,x]==' '||g.map[y+1,x]=='R'))
177 + if(rocky(g.map[y+1,x-1]) && (g.map[y,x-1]=='\\'||rocky(g.map[y,x-1]))
178 + && (g.map[y+1,x]==' '||g.map[y+1,x]=='R'))
171 179 return true;
172 180 if(rocky(g.map[y+1,x+1]) && rocky(g.map[y,x+1]) && (g.map[y+1,x]==' '||g.map[y+1,x]=='R'))
173 181 return true;
174 - if(rocky(g.map[y,x-1]) && (g.map[y-1,x-1]=='\\'||rocky(g.map[y-1,x-1])) && (g.map[y-1,x]==' '||g.map[y-1,x]=='R'))
182 + if(rocky(g.map[y,x-1]) && (g.map[y-1,x-1]=='\\'||rocky(g.map[y-1,x-1]))
183 + && (g.map[y-1,x]==' '||g.map[y-1,x]=='R'))
175 184 return true;
176 185 if(rocky(g.map[y,x+1]) && rocky(g.map[y-1,x+1]) && (g.map[y-1,x]==' '||g.map[y-1,x]=='R'))
177 186 return true;
178 187 return false;
179 188 }
180 189
181 190 // avoid directly below '*'
................................................................................
300 309 }
301 310 return [];
302 311 }
303 312 return (danger_ok ? [] : tryA()) ~ tryB() ~ tryC();
304 313 }
305 314 }
306 315
307 -class Solver_2(Solver)
316 +class Solver_2(SubSolver) : Solver
308 317 {
309 318 string plan;
310 319 bool plan_broken = true;
311 320
312 321 Game g;
313 322 this(in Game g)
314 323 {
315 324 this.g = g.clone();
316 325 make_plan(g);
317 326 }
318 327
319 - Tuple!(Solver,string) run_sub_solver(in Game g)
328 + Tuple!(SubSolver,string) run_sub_solver(in Game g)
320 329 {
321 330 string log;
322 - auto s = new Solver(g);
331 + auto s = new SubSolver(g);
323 332 while(!g.cleared && !g.dead && plan.length<=g.map.H*g.map.W) {
324 333 char c = s.single_step();
325 334 if( c == 'A' )
326 335 break;
327 336 log ~= c;
328 337 }
329 338 while(log.length>0 && log[$-1]=='W')
330 339 log.length--;
331 340 return tuple(s, log);
332 341 }
333 342
334 343 void make_plan(in Game g) {
335 344 plan_broken = false;
336 - Tuple!(Solver,string) x = run_sub_solver(g);
345 + Tuple!(SubSolver,string) x = run_sub_solver(g);
337 346 plan = x[1];
338 347 if(x[0].g.cleared)
339 348 return;
340 349 modify_plan(g, x[0].g.score);
341 350 }
342 351
343 352 void modify_plan(in Game ini, long unmod)
................................................................................
359 368 plan = cand[0];
360 369 }
361 370
362 371 Tuple!(string,long) try_plan(string c, in Game g)
363 372 {
364 373 Game gg = g.clone();
365 374 foreach(cc;c)gg.command(cc);
366 - Tuple!(Solver, string) x = run_sub_solver(gg);
375 + Tuple!(SubSolver, string) x = run_sub_solver(gg);
367 376 return tuple(x[1], x[0].g.score);
368 377 }
369 378
370 379 char single_step() {
371 380 if(plan_broken)
372 381 make_plan(g);
373 382 if(plan.empty)
................................................................................
385 394 plan_broken = true;
386 395 }
387 396 else
388 397 plan = plan[1..$];
389 398 }
390 399 }
391 400
401 +class MasterSolver : Solver
402 +{
403 + this(in Game g)
404 + {
405 + int SIZE = g.map.H * g.map.W;
406 + if( SIZE <= 32*32 )
407 + sub = new Solver_2!(Solver_1)(g);
408 + else if( SIZE <= 100*100 )
409 + sub = new Solver_1(g);
410 + else
411 + sub = new Solver_1(g);
412 + }
413 +
414 + private Solver sub;
415 + char single_step() { return sub.single_step(); }
416 + void force(char c) { sub.force(c); }
417 +}
418 +
419 +alias MasterSolver MainSolver;
392 420 //alias Solver_2!(Solver_1) MainSolver;
393 421 //alias Solver_1 MainSolver;
394 -alias Solver_0 MainSolver;
422 +//alias Solver_0 MainSolver;