/* This function adds the semeai related move reasons, using the information * stored in the dragon2 array. * * If the semeai had an uncertain result, and there is a owl move with * certain result doing the same, we don't trust the semeai move. */ void semeai_move_reasons(int color) { int other = OTHER_COLOR(color); int d; int liberties; int libs[MAXLIBS]; int r; int resulta, resultb, semeai_move, s_result_certain; for (d = 0; d < number_of_dragons; d++) if (dragon2[d].semeais && DRAGON(d).status == CRITICAL) { if (DRAGON(d).color == color && dragon2[d].semeai_defense_point && (dragon2[d].owl_defense_point == NO_MOVE || dragon2[d].semeai_defense_certain >= dragon2[d].owl_defense_certain)) { /* My dragon can be defended. */ add_semeai_move(dragon2[d].semeai_defense_point, dragon2[d].origin); DEBUG(DEBUG_SEMEAI, "Adding semeai defense move for %1m at %1m\n", DRAGON(d).origin, dragon2[d].semeai_defense_point); if (neighbor_of_dragon(dragon2[d].semeai_defense_point, dragon2[d].semeai_defense_target) && !neighbor_of_dragon(dragon2[d].semeai_defense_point, dragon2[d].origin) && !is_self_atari(dragon2[d].semeai_defense_point, color)) { /* If this is a move to fill the non-common liberties of the * target, and is not a ko or snap-back, then we try all * non-common liberties of the target and add all winning * moves to the move list. */ liberties = findlib(dragon2[d].semeai_defense_target, MAXLIBS, libs); for (r = 0; r < liberties; r++) { if (!neighbor_of_dragon(libs[r], dragon2[d].origin) && !is_self_atari(libs[r], color) && libs[r] != dragon2[d].semeai_defense_point) { owl_analyze_semeai_after_move(libs[r], color, dragon2[d].semeai_defense_target, dragon2[d].origin, &resulta, &resultb, &semeai_move, 1, &s_result_certain, 0); if (resulta == 0 && resultb == 0) { add_semeai_move(libs[r], dragon2[d].origin); DEBUG(DEBUG_SEMEAI, "Adding semeai defense move for %1m at %1m\n", DRAGON(d).origin, libs[r]); } } } } } else if (DRAGON(d).color == other && dragon2[d].semeai_attack_point && (dragon2[d].owl_attack_point == NO_MOVE || dragon2[d].owl_defense_point == NO_MOVE || dragon2[d].semeai_attack_certain >= dragon2[d].owl_attack_certain)) { /* Your dragon can be attacked. */ add_semeai_move(dragon2[d].semeai_attack_point, dragon2[d].origin); DEBUG(DEBUG_SEMEAI, "Adding semeai attack move for %1m at %1m\n", DRAGON(d).origin, dragon2[d].semeai_attack_point); if (neighbor_of_dragon(dragon2[d].semeai_attack_point, dragon2[d].origin) && !neighbor_of_dragon(dragon2[d].semeai_attack_point, dragon2[d].semeai_attack_target) && !is_self_atari(dragon2[d].semeai_attack_point, color)) { liberties = findlib(dragon2[d].origin, MAXLIBS, libs); for (r = 0; r < liberties; r++) { if (!neighbor_of_dragon(libs[r], dragon2[d].semeai_attack_target) && !is_self_atari(libs[r], color) && libs[r] != dragon2[d].semeai_attack_point) { owl_analyze_semeai_after_move(libs[r], color, dragon2[d].origin, dragon2[d].semeai_attack_target, &resulta, &resultb, &semeai_move, 1, &s_result_certain, 0); if (resulta == 0 && resultb == 0) { add_semeai_move(libs[r], dragon2[d].origin); DEBUG(DEBUG_SEMEAI, "Adding semeai attack move for %1m at %1m\n", DRAGON(d).origin, libs[r]); } } } } } } }
/* This function adds the semeai related move reasons, using the information * stored in the dragon2 array. * * If the semeai had an uncertain result, and there is a owl move with * certain result doing the same, we don't trust the semeai move. */ void semeai_move_reasons(int color) { int other = OTHER_COLOR(color); int d; int liberties; int libs[MAXLIBS]; int r; for (d = 0; d < number_of_dragons; d++) if (dragon2[d].semeais && DRAGON(d).status == CRITICAL) { if (DRAGON(d).color == color && dragon2[d].semeai_defense_point && (dragon2[d].owl_defense_point == NO_MOVE || dragon2[d].semeai_defense_certain >= dragon2[d].owl_defense_certain)) { /* My dragon can be defended. */ add_semeai_move(dragon2[d].semeai_defense_point, dragon2[d].origin); DEBUG(DEBUG_SEMEAI, "Adding semeai defense move for %1m at %1m\n", DRAGON(d).origin, dragon2[d].semeai_defense_point); if (neighbor_of_dragon(dragon2[d].semeai_defense_point, dragon2[d].semeai_defense_target) && !neighbor_of_dragon(dragon2[d].semeai_defense_point, dragon2[d].origin) && !is_self_atari(dragon2[d].semeai_defense_point, color)) { /* If this is a move to fill the non-common liberties of the * target, and is not a ko or snap-back, then we mark all * non-common liberties of the target as potential semeai moves. */ liberties = findlib(dragon2[d].semeai_defense_target, MAXLIBS, libs); for (r = 0; r < liberties; r++) { if (!neighbor_of_dragon(libs[r], dragon2[d].origin) && !is_self_atari(libs[r], color) && libs[r] != dragon2[d].semeai_defense_point) add_potential_semeai_defense(libs[r], dragon2[d].origin, dragon2[d].semeai_defense_target); } } } else if (DRAGON(d).color == other && dragon2[d].semeai_attack_point && (dragon2[d].owl_attack_point == NO_MOVE || dragon2[d].owl_defense_point == NO_MOVE || dragon2[d].semeai_attack_certain >= dragon2[d].owl_attack_certain)) { /* Your dragon can be attacked. */ add_semeai_move(dragon2[d].semeai_attack_point, dragon2[d].origin); DEBUG(DEBUG_SEMEAI, "Adding semeai attack move for %1m at %1m\n", DRAGON(d).origin, dragon2[d].semeai_attack_point); if (neighbor_of_dragon(dragon2[d].semeai_attack_point, dragon2[d].origin) && !neighbor_of_dragon(dragon2[d].semeai_attack_point, dragon2[d].semeai_attack_target) && !is_self_atari(dragon2[d].semeai_attack_point, color)) { liberties = findlib(dragon2[d].origin, MAXLIBS, libs); for (r = 0; r < liberties; r++) { if (!neighbor_of_dragon(libs[r], dragon2[d].semeai_attack_target) && !is_self_atari(libs[r], color) && libs[r] != dragon2[d].semeai_attack_point) add_potential_semeai_attack(libs[r], dragon2[d].origin, dragon2[d].semeai_attack_target); } } } } }