// logic for computer's turn int computer_move() { if ( blocking_win() == 1) return( 1 ); if ( check_corner() == 1) return( 1 ); if ( check_row() == 1) return( 1 ); return( 0 ); }
/** * \brief Checks if the motor finished the necessary corner * * \param motor Used to specify a reference to the motor that needs to be checked * * \return void */ void check_movement(volatile motor_t* motor) { if (motor->corner!=C0) { switch (motor->corner) { case C90: { check_corner(C90); } break; case C45: { check_corner(C45) } break; case CIRCLE_RADIUS: { check_corner(CIRCLE_RADIUS) } break; case WALL_FORWARD: { check_corner(WALL_FORWARD) } break; case WALL_1: { check_corner(WALL_1) } break; case WALL_2: { check_corner(WALL_2) } break; case WALL_3: { check_corner(WALL_3) } break; case WALL_4: { check_corner(WALL_4) } break; default: { motor->rpm = 0; motor->corner = C0; } break; } } }
// LOSfinder::calculateVisisble calculates visibility list of map from given map point // The line-of-sigh check works as follows: // from the center of given tile to every tile corner of the viewport ray is casted // ray is casted from center of tile to corners, so it is never aligned to either axis // if ray passes only transparent tiles on its way to given corner then the corner is visible // if ray passes through corner then it checks sibling tiles. If both of them are not transparent then ray blocks // if ray passes through edge it checks both adjasent tiles. They both must be transparent, otherwise ray blocks // if tile has at least one visible corner then this tile is visible // otherwise tile is invisible std::list<PosPoint>* LOSfinder::CalculateVisisble(std::list<PosPoint>* retlist, int posx, int posy, int posz) { Clear(); const int VISIBLE_TILES_SIZE = 4 * (SIZE_H_SQ + 2) * (SIZE_W_SQ + 2); char* visible_tiles = new char[VISIBLE_TILES_SIZE]; for (int i = 0; i < VISIBLE_TILES_SIZE; ++i) { visible_tiles[i] = 0; } PosPoint source( pos2corner(posx) + RAY_MULTIPLIER / 2, pos2corner(posy) + RAY_MULTIPLIER / 2, pos2corner(posz) + 1); for (int i = -SIZE_W_SQ; i < SIZE_W_SQ; ++i) { for (int j = -SIZE_H_SQ; j < SIZE_H_SQ; ++j) { PosPoint p(pos2corner(posx + i), pos2corner(posy + j), pos2corner(posz)); if (!check_corner(p)) { continue; } // TODO: we can check that all siblings of this corner are visible // so check is unnessesary if (ray_trace(source, p)) { // add all tiles with this corner to visible list mark_tiles_of_corner_as_visible( retlist, corner_point2point(p), corner_point2point(source), visible_tiles); } } } delete[] visible_tiles; return retlist; }
int main() { int sum, pos; scanf("%d%d", &rows, &cols); area = cols*rows; for (pos = 0; pos < area; pos++) { j[pos] = pos % cols; i[pos] = pos / cols; up[pos] = pos < cols ? SAFE_SPOT : pos - cols; down[pos] = pos >= area - cols ? SAFE_SPOT : pos + cols; left[pos] = pos % cols == 0 ? SAFE_SPOT : pos - 1; right[pos] = (pos+1) % cols == 0 ? SAFE_SPOT : pos + 1; } debug(("List of LoR's:")); for (pos = 0, sum = 0; pos < area; pos++) { scanf("%d", start->map + pos); sum += start->map[pos]; if (start->map[pos] == 1 && i[pos] && j[pos] && i[pos] < rows-1 && j[pos] < cols-1) { start->map[pos] = 5; late_or_early[lor_count++] = pos; debug(("%d,", pos)); } } debug(("\b \n")); start->level = 0; start->lor_num = -1; start->map[area] = 1; /* stopper for unmake */ real_deathcount = area*3 - cols - rows - sum; #ifdef ONLINE_JUDGE /* short-circuit check */ if (real_deathcount%4) { printf("No\n"); return 0; } #endif real_deathcount /= 4; #define check_corner(a) do { \ switch (start->map[a] == 1) { \ case 4: \ goto no; \ case 3: \ start->knowledge[a] = EARLY; \ break; \ case 1: \ start->knowledge[a] = LATE; \ break; \ default: \ break; \ } \ } while (0); check_corner(0); check_corner(cols-1); check_corner(area-1); check_corner(area-cols); #define check_side(a) do { \ switch (start->map[a]) { \ case 4: \ start->knowledge[a] = EARLY; \ break; \ case 1: \ start->knowledge[a] = LATE; \ break; \ default: \ break; \ } \ } while (0); /* first and last rows */ for (pos = 1; pos < cols - 1; pos++) { check_side(pos); if (start->knowledge[pos] == EARLY && EARLY_NEIGH_COUNT(start->knowledge,pos) || start->knowledge[pos] == LATE && LATE_NEIGH_COUNT(start->knowledge,pos)) goto no; check_side(area - pos); if (start->knowledge[area-pos] == EARLY && EARLY_NEIGH_COUNT(start->knowledge,area-pos) || start->knowledge[area-pos] == LATE && LATE_NEIGH_COUNT(start->knowledge,area-pos)) goto no; } for (pos = cols; pos < area - cols; pos+=cols) { check_side(pos); if (start->knowledge[pos] == EARLY && EARLY_NEIGH_COUNT(start->knowledge,pos) || start->knowledge[pos] == LATE && LATE_NEIGH_COUNT(start->knowledge,pos)) goto no; check_side(area - pos); if (start->knowledge[area-pos] == EARLY && EARLY_NEIGH_COUNT(start->knowledge,area-pos) || start->knowledge[area-pos] == LATE && LATE_NEIGH_COUNT(start->knowledge,area-pos)) goto no; } if (solve(start) == 0) { printf("Yes\n"); for (pos = area; pos--; ) printf("%d %d\n", solution[pos] / cols + 1, solution[pos] % cols + 1); } else { no: printf("No\n"); } }