// jumpsaround - jumper game
// (c) 2011 Alexander Kulbartsch

#include <stdio.h>

#define SIZEX 6
#define SIZEY 5

static signed int jump[8][2] = {{-1,-2}, {1,-2}, {-2,-1}, {2,-1}, {-2,1}, {2,1}, {-1,2}, {1,2}}; 

char board[SIZEX][SIZEY];
char iters[SIZEX*SIZEY];
long int solutions; 
long int roundtrips;

void jumpto(signed char x, signed char y, int iter, char arity);
void printboard();


int main (int argc, const char * argv[]) {
    printf("Hello, Jumper!\n");
	
	// init
	for	(int i = 0; i < SIZEX; i++) {
	    for (int j = 0; j < SIZEY; j++) {
			board[i][j] = 0;
		}
	}
	for	(int i = 0; i < (SIZEX*SIZEY); i++) iters[i] = 0;
	iters[0] = ' ';

	jumpto(0, 0, 1, 0);
    
	printf("I am done.\n");
	
	return 0;
}


void jumpto(signed char x, signed char y, int iter, char arity) {

   	// check if position is on the board
	if ( x<0 || x>(SIZEX-1) || y<0 || y>(SIZEY-1) ) return;
    
    // check if field on board is still empty
	if ( board[x][y] != 0 ) return;

	// ok - store position
	board[x][y] = iter;
	iters[iter] = arity + '0';
	
	// finished?
	if (iter >= SIZEX*SIZEY ) {

		// check for jumper roundtrips
		signed int round = 0;
		for (int i = 0; i < 8; i++) {
			signed char nx = x + jump[i][0]; 
			signed char ny = y + jump[i][1];
            // check if position is on the board
			if ( nx<0 || nx>(SIZEX-1) || ny<0 || ny>(SIZEY-1) ) continue;
			// detect roundtrip
			if ( board[nx][ny] == 1 ) { round = 1; roundtrips++; break; } // True
		}
        solutions++;
		printboard(round);

		// end this iteration
		board[x][y] = 0;
	    iters[iter] = 0;
		return;
	}
	
	// try next jump
    for (int i = 0; i < 8; i++) {
		signed char nx = x + jump[i][0]; 
		signed char ny = y + jump[i][1]; 
		jumpto(nx, ny, iter + 1, i);
	}
	
	// this iteration is done
	board[x][y] = 0;
	iters[iter] = 0;
	
}

void printboard(int round) {
	printf("===== Solution # %ld (Roundtripps: %ld) ====== ", solutions, roundtrips);
	if (round) printf(" *** Roundtrip *** ");
	printf("\n");
    for	(int i = 0; i < SIZEY; i++) {
	    for (int j = 0; j < SIZEX; j++) {
			printf("%2i:", board[j][i]);
		}
		printf("\n");
	}
	printf("\n");
}

// EOF
