
/**
 * A complex board is a specialization of Board where we can represent it as a
 * 2-D matrix of boolean values. When true, a Queen has been placed. When false,
 * it is considered "available" for placement
 * 
 * @author Professor Killian
 *
 */
public class ComplexBoard implements Board {
	private int size;
	private boolean[][] board;

	/**
	 * Constructs a new Board of size <em>n</em>
	 * @param n the size of the Board
	 */
	public ComplexBoard(int n) {
		size = n;
		board = new boolean[n][n];
	}

	@Override
	public boolean canPlace(int r, int c) {
		if (r < 0 || r >= size || c < 0 || c >= size) {
			throw new RuntimeException("Tried to place out of bounds");
		}
		for (int i = 0; i < size; ++i) {
			if (board[r][i]) {
				return false;
			}
			if (board[i][c]) {
				return false;
			}
		}
		for (int i = 1; i < size - 1; ++i) {
			if (r - i >= 0 && c - i >= 0 && board[r - i][c - i]) {
				return false;
			}
			if (r - i >= 0 && c + i < size && board[r - i][c + i]) {
				return false;
			}
			if (r + i < size && c - i >= 0 && board[r + i][c - i]) {
				return false;
			}
			if (r + i < size && c + i < size && board[r + i][c + i]) {
				return false;
			}
		}
		return true;
	}

	@Override
	public void place(int r, int c) {
		board[r][c] = true;
	}

	@Override
	public void unplace(int r, int c) {
		board[r][c] = false;
	}

	@Override
	public void print() {
		for (boolean[] row : board) {
			for (boolean val : row) {
				if (val) {
					System.out.print('*');
				} else {
					System.out.print('.');
				}
				System.out.print(' ');
			}
			System.out.println();
		}
	}

	@Override
	public int size() {
		return size;
	}
}
