jquery - How to organize elements (pieces of Tetris) recursively -
i'm learning recursion need reference on how start making algorithm. need organize blocks use pieces, max possible fill of board. all.
here rather naive implementation of algorithm started.
it looking perfect solution (where board entirely filled) , exit finds one. work expected example board, may run forever other boards not have simple perfect solution, or no perfect solution @ all.
a better algorithm would:
- look best solution board (not perfect one)
- use more heuristics speed search
the refinement in algorithm use of hash table avoid visiting same board twice, when 2 different move combinations produce same configuration.
each row of board represented byte , each piece represented 2x2 bits.
var b = [ // initial board 0b00000000, 0b00000000, 0b00000100, 0b00000000, 0b00000000, 0b00000000, 0b00000000, 0b00000000 ], piece = [ // bitmasks of pieces [ top_bitmask, bottom_bitmask ] [ 0b11, 0b01 ], [ 0b11, 0b10 ], [ 0b01, 0b11 ], [ 0b10, 0b11 ] ], // hash table of visited boards hash = {}, // statistics node = 0, hit = 0; function solve(sol) { var x, y, p, s; // compute hexadecimal key representing current board var key = ((b[0] | (b[1] << 8) | (b[2] << 16) | (b[3] << 24)) >>> 0).tostring(16) + '-' + ((b[4] | (b[5] << 8) | (b[6] << 16) | (b[7] << 24)) >>> 0).tostring(16); node++; if(hash[key]) { // abort if board visited hit++; return false; } if(key == 'ffffffff-ffffffff') { // return current solution if board entirely filled return sol; } // save board in hash table hash[key] = true; // each position , each type of piece ... for(y = 0; y < 7; y++) { for(x = 0; x < 7; x++) { for(p = 0; p < 4; p++) { // ... see if can insert piece @ position if(!(b[y] & (piece[p][0] << x)) && !(b[y + 1] & (piece[p][1] << x))) { // make move b[y] ^= piece[p][0] << x; b[y + 1] ^= piece[p][1] << x; // add move solution , process recursive call s = solve(sol.concat(x, y, p)); // unmake move b[y] ^= piece[p][0] << x; b[y + 1] ^= piece[p][1] << x; // if have solution, return if(s) { return s; } } } } } return false; } function display(sol) { var n, x, y, html = ''; for(n = 0; n < 64; n++) { html += '<div class="cell"></div>'; } $('#container').html(html); for(n = 0; n < sol.length; n += 3) { for(y = 0; y < 2; y++) { for(x = 0; x < 2; x++) { if(piece[sol[n + 2]][y] & (1 << x)) { $('.cell').eq(7 - sol[n] - x + (sol[n + 1] + y) * 8) .addclass('c' + sol[n + 2]); } } } } } settimeout(function() { display(solve([])); console.log(node + ' nodes visited'); console.log(hit + ' hash table hits'); }, 500); #container { width:160px; height:160px } .cell { width:19px; height:19px; margin:1px 1px 0 0; background-color:#777; float:left } .c0 { background-color:#fb4 } .c1 { background-color:#f8f } .c2 { background-color:#4bf } .c3 { background-color:#4d8 } <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> <div id="container">searching...</div> 
Comments
Post a Comment