private void check_small_diagonal(int diagonal, ref bool white_made_a_line, ref bool black_made_a_line) { int sequence_size = 0; for (int i = 0; i < 5; i++) { hole_state hole = hole_state.is_empty; switch (diagonal) { case 0: hole = board[(i + 1) * 6 + i]; break; case 1: hole = board[i * 6 + i + 1]; break; case 2: hole = board[(i + 1) * 6 + 5 - i]; break; case 3: hole = board[i * 6 + 4 - i]; break; default: break; } if (hole == hole_state.is_empty) { break; //speed up, can't be any line there } if (hole == hole_state.has_white && sequence_size >= 0) { if (sequence_size < 0) { return; //speedup } ++sequence_size; if (sequence_size == 5) { white_made_a_line = true; break; } } else if (hole == hole_state.has_black && sequence_size <= 0) { if (sequence_size > 0) { return; //speedup } --sequence_size; if (sequence_size == -5) { black_made_a_line = true; break; } } else { sequence_size = 0; } } }
/// <summary> /// check if game has ended, and if there is a winner /// </summary> /// <param name="player"> player = null if draw or game did not end, false if whites win (= to turn value)</param> /// <returns>true if ended</returns> public bool game_ended(out bool?player) { bool board_full = true; bool white_made_a_line = false; bool black_made_a_line = false; int sequence_size;//counts positive 4 white and negative 4 black to avoid using another var //could also check horizontals and verticals in one iteration using more memory, not sure what is best //check horizontals and if board is full for (int line = 0; line < 6; ++line) { if (board_full) { if (board[line * 6] == hole_state.is_empty) { board_full = false; } } sequence_size = (int)board[line * 6]; for (int row = 1; row < 6; ++row) { hole_state hole = board[line * 6 + row]; if (hole == hole_state.is_empty) { board_full = false; if (row != 5) { break; //speed up, can't be any line there } } if (hole == hole_state.has_white) { if (sequence_size < 0) { sequence_size = 0; } ++sequence_size; if (sequence_size == 5) { white_made_a_line = true; break; } } else if (hole == hole_state.has_black) { if (sequence_size > 0) { sequence_size = 0; } --sequence_size; if (sequence_size == -5) { black_made_a_line = true; break; } } else { sequence_size = 0; } } } //check verticals for (int row = 0; row < 6; ++row) { sequence_size = (int)board[row]; for (int line = 1; line < 6; ++line) { hole_state hole = board[line * 6 + row]; if (hole == hole_state.is_empty) { if (line != 5) { break; //speed up, can't be any line there } } if (hole == hole_state.has_white) { if (sequence_size < 0) { sequence_size = 0; } ++sequence_size; if (sequence_size == 5) { white_made_a_line = true; break; } } else if (hole == hole_state.has_black) { if (sequence_size > 0) { sequence_size = 0; } --sequence_size; if (sequence_size == -5) { black_made_a_line = true; break; } } else { sequence_size = 0; } } } //check 2 larger diagonals sequence_size = (int)board[0]; for (int i = 1; i < 6; i++) { hole_state hole = board[i * 6 + i]; if (hole == hole_state.is_empty) { if (i != 5) { break; //speed up, can't be any line there } } if (hole == hole_state.has_white) { if (sequence_size < 0) { sequence_size = 0; } ++sequence_size; if (sequence_size == 5) { white_made_a_line = true; break; } } else if (hole == hole_state.has_black) { if (sequence_size > 0) { sequence_size = 0; } --sequence_size; if (sequence_size == -5) { black_made_a_line = true; break; } } else { sequence_size = 0; } } sequence_size = (int)board[5]; for (int i = 1; i < 6; i++) { hole_state hole = board[i * 6 + 5 - i]; if (hole == hole_state.is_empty) { if (i != 5) { break; //speed up, can't be any line there } } if (hole == hole_state.has_white) { if (sequence_size < 0) { sequence_size = 0; } ++sequence_size; if (sequence_size == 5) { white_made_a_line = true; break; } } else if (hole == hole_state.has_black) { if (sequence_size > 0) { sequence_size = 0; } --sequence_size; if (sequence_size == -5) { black_made_a_line = true; break; } } else { sequence_size = 0; } } //check 4 smaller diagonals for (int i = 0; i < 4; i++) { check_small_diagonal(i, ref white_made_a_line, ref black_made_a_line); } if (white_made_a_line && !black_made_a_line) { player = whites_turn; } else if (!white_made_a_line && black_made_a_line) { player = blacks_turn; } else { player = null; } if (turn_state == turn_state_rotate) { board_full = false; } return(board_full || black_made_a_line || white_made_a_line); }