언덕에서 부활절 달걀 사냥


17

이스터 에그 헌트

봇은 계란을 찾기 전에 계란을 찾습니다. 봇 행복합니다.

개요

이것은 부활절과 부활절 달걀 사냥 전통을 기리기위한 도전입니다!

봇은 대각선을 포함하여 모든 방향으로 두 공간의 비전을 가지고 있습니다. 계란을 찾고 있으며 가장 많은 계란을 얻는 사람은 이깁니다!

보드

보드 o는 부활절 달걀 인 #s, 벽인 *s, 다른 플레이어 인 s, 빈 공간 인 s로 구성됩니다.

  • 가장자리 길이가있는 정사각형이됩니다. (number of entries) * 3 .
  • 벽으로 둘러싸 일 것입니다.
  • 벽 안에는 무작위로 배치 된 직선 벽 #이 있으며, 길이는 2에서 10 사이의 임의의 길이를 갖습니다. 있을 것이다(number of entries) * 3그들 중에 입니다.
  • 계란은 무작위로 배치됩니다. (number of entries) * 4그들 중 하나 가있을 것이고 , 그들은 빈칸에서만 생성됩니다 ( 칸 ) 입니다.
  • 보드 생성 프로세스가 제대로 작동하려면 전체가 7 개 이상 있어야합니다.

다음은 테스트 할 임의의 보드생성하는 JSFiddle입니다 . 예를 들면 다음과 (number of entries) = 7같습니다.

#####################
#        o         ##
#    #    o        ##
#    #o    ######  ##
######     #       ##
## o #     #       ##
##  o#   #o#    o o##
##   #o  # # o  #   #
##   # o # #    #   #
##  ##   # #  o #   #
##  #    #  o   # # #
##  # o  #   ## # # #
##  #           # # #
# o #          ## # #
# o oo         ##o  #
#o  ####### oo ##   #
#        #      #   #
#   o o o#          #
#   o ####   o     o#
#                   #
#####################

보드가 생성 된 후 각 플레이어는 임의의 사각형 (빈 공간) 에 배치됩니다 .

입력

6 줄의 입력을받습니다. 처음 다섯 줄은 시야 (보드의 경계를 벗어난 공간은로 표시되고 X중간 공간은 항상 *)로 표시되며 여섯 번째 줄은 비어 있습니다 (처음에는).

산출

세 줄을 출력합니다. 먼저, 이동하려는 방향 :

1  2  3
8 YOU 4
7  6  5

(이동하지 않으려는 경우 9는 작동하지 않습니다.) 둘째, A공격, 수사 중 하나 C또는N (이것은 곧 깊이 설명됩니다), 세 번째 줄은 최대 1024 길이의 문자열입니다 봇의 기억이 될 것입니다. 원하는 용도로 사용하거나 비워 둘 수 있습니다. 이 메모리는 다음 실행시 프로그램에 대한 여섯 번째 입력 라인이됩니다.

추가 출력 라인은 모두 무시되며 라인이 하나만 있으면 두 번째 라인은 공백으로 간주됩니다.

움직이는

이동 한 위치를 결정하는 데 다음 프로세스가 사용됩니다.

  • 이사 할 때 빈 공간에있게되면 ( )에 도달하면 플레이어가 해당 공간에 배치됩니다.
  • 벽에 닿으면# )에 들어가면 이동이 무시되고 턴을 잃습니다.
  • 달걀 ( o) 또는 플레이어 ( *)로 끝나는 경우이 정보는 모든 사람이 이동 한 후에 저장되며 사용됩니다.

모두가 움직 인 후에 모호성이 해결됩니다.

같은 공간에 착륙 한 두 명의 플레이어가 있다면 전투가 발생합니다! 이것은 A/ C/ N가 재생되는 곳입니다. Attack의 비트 N(일반 공격) othing, Nothing 비트 Counter (당신이 카운터 아무것도 할 수 없습니다), 그리고 C비트는 ounter A(역습) ttack. 이 싸움에서이긴 플레이어는 자신의 광장에 머무르고, 잃은 플레이어는 처음 시작한 원래의 광장으로 돌아갑니다. 동점 일 경우 두 선수 모두 원래 위치로 돌아갑니다.

잃거나 묶인 플레이어가 원래 위치로 돌아가서 다른 플레이어가있는 경우, 전투가 없으며 다른 플레이어도 원래 공간으로 되돌아갑니다. 경우 공간은 다른 선수가 플레이어는 되돌아 가고 모든 플레이어가 다른 공간에있을 때까지 계속됩니다.

한 공간에 3 명 이상의 플레이어가있는 경우 모두 원래 위치로 되돌아갑니다.

어떤 선수가 여전히 계란 위에 서 있다면 ...

  • 플레이어가를 선택 A하면 알이 파괴됩니다.
  • 플레이어가를 선택 C하면 아무 일도 일어나지 않으며 플레이어는 원래 공간으로 되돌아갑니다.
  • 플레이어가을 선택 N하면 플레이어는 알을 줍습니다! 플레이어의 점수는 1 씩 증가하고 알은 제거됩니다.

언어

각 참가자 간의 공정성을 보장하기 위해 Windows, OSX 및 Linux에서 자유롭게 사용할 수있는 모든 언어를 사용할 수 있습니다. 코드를 자유롭게 실행할 수 없지만 형식으로 컴파일 또는 패키지 할 수있는 경우이 형식도 답에 포함하십시오. 코드를보다 일반적인 언어 (예 : CoffeeScript-> JavaScript)로 컴파일 할 수 있다면 이상적입니다.

채점

당신의 점수는 당신이 열 번 실행에서 수집하는 평균 계란 수입니다. 모든 알이 모이거나 (number of entries * 25)회전이 지나면 런이 종료됩니다 . 모든지도에 도달 할 때까지지도를 계속 생성하여 각지도의 모든 계란에 도달 할 수 있는지 수동으로 확인하겠습니다.

스코어 보드

다음 조건이 모두 충족되면 스코어 보드가 추가됩니다.

  • 양수 또는 0 점 (비공개되지 않음)을 가진 7 개 이상의 유효한 출품작이 제출되었습니다.
  • 이 도전을 만든 후 최소 48 시간이 지났습니다 (UTC 14:23).

규칙이 명확하지 않은 경우 설명을 추가하는 경우를 제외하고이 사전 대회 기간 동안 규칙은 변경되지 않습니다. 점수 판이 완성되면 테스트 프로그램도 여기에 게시되어 출품작을 테스트 할 수 있습니다. 이것에 대한 테스트 코드는 여전히 진행 중이지만 재생할 수 있으며 작동합니다. 여기 GitHub 저장소가 있습니다.


4
7 개의 출품작이 게시되기 전에 시험 프로그램을받을 수 있습니까? "벙어리"테스트 봇에 대해 게시 한 경우에도 게시 하기 전에 테스트하고 싶습니다 . 이것은 다른 사람들이 게시 할 때까지 게시 하지 않는 것이 큰 이점을 제공합니다 .
Geobits

1
돌아 오는 플레이어에 대해서. 그래서 나는 운이 나쁘고 상대를 상대로 이길 수 있었지만 다른 선수에게 물러서서 우리 전투 장소로 돌아가는 캐스케이드를 시작합니다. (확실하지 않은 경우, 예를 들어 github 요점을 게시 할 것입니다)
Martin Ender

1
샘플 제어 프로그램은 여기서 매우 유용합니다.
starbeamrainbowlabs

3
나는 메모리 라인 아이디어를 좋아한다
Einacio

2
또한 규칙의 의미를 알고 있습니까? 플레이어 (A)가을 선택 9하면 의미있는 공격을 할 수 없습니다. 다른 선수 (B)가 해당 선수 광장에 들어서서 이기면 A는 원래 광장으로 다시 이동합니다 (동일 함). 그러나 이제 A와 B가 모두 있기 때문에 충돌이 발생하므로 B는 자신의 광장으로 돌아 가야합니다. 따라서 결과는 실제 전투와 무관하며 B는 항상 초기 광장으로 돌아가고 A는 항상 그대로 유지됩니다. 그것은 내가 다른 사람을위한 길을 막음으로써 또 다른 제출을 도울 수있는 둘 다 쓸 수있게 해줄 것입니다.
Martin Ender

답변:


3

카르 토고 퍼

여기 또 다른 제출물이 있습니다.이 제출물은 실제로 경쟁력이 있어야합니다. 다시, 루비에 있습니다. 로 실행하십시오 ruby cartogophers.rb. 예상보다 시간이 많이 걸렸습니다 ...

require 'zlib'
require 'base64'

def encode map, coords
    zipped = Zlib::Deflate.deflate map.join
    encoded = Base64.encode64(zipped).gsub("\n",'')
    "#{coords[:x]}|#{coords[:y]}|#{map.length}|#{encoded}"
end

def decode memory
    memory =~ /^(\d+)[|](\d+)[|](\d+)[|](.*)$/
    coords = {x: $1.to_i, y: $2.to_i}
    n_rows = $3.to_i
    encoded = $4
    decoded = Base64.decode64 encoded
    unzipped = Zlib::Inflate.inflate decoded
    n_cols = unzipped.length / n_rows;
    return unzipped.scan(/.{#{n_cols}}/), coords
end

def update map, fov, coords
    if coords[:x] < 2
        map.map! { |row| '?' << row }
        coords[:x] += 1
    elsif coords[:x] >= map[0].length - 2
        map.map! { |row| row << '?' }
    end

    if coords[:y] < 2
        map.unshift '?' * map[0].length
        coords[:y] += 1
    elsif coords[:y] >= map.length - 2
        map.push '?' * map[0].length
    end

    fov.each_index do |i|
        map[coords[:y]-2+i][coords[:x]-2, 5] = fov[i]
    end

    return map, coords
end

def clean_up map
    map.each do |row|
        row.gsub!('*', ' ')
    end
end

DIRECTIONS = [
    [],
    [-1,-1],
    [ 0,-1],
    [ 1,-1],
    [ 1, 0],
    [ 1, 1],
    [ 0, 1],
    [-1, 1],
    [-1, 0],
    [ 0, 0]
]

def move_to dir, coords
    {
        x: coords[:x] + DIRECTIONS[dir][0],
        y: coords[:y] + DIRECTIONS[dir][1]
    }
end

def get map, coords
    if coords[:x] < 0 || coords[:x] >= map[0].length ||
       coords[:y] < 0 || coords[:y] >= map.length
        return '?'
    end
    map[coords[:y]][coords[:x]]
end

def set map, coords, value
    unless coords[:x] < 0 || coords[:x] >= map[0].length ||
       coords[:y] < 0 || coords[:y] >= map.length
        map[coords[:y]][coords[:x]] = value
    end
    map[coords[:y]][coords[:x]]
end

def scan_surroundings map, coords
    not_checked = [coords]
    checked = []
    cost = { coords => 0 }
    direction = { coords => 9 }
    edges = {}

    while not_checked.length > 0
        current = not_checked.pop

        checked.push current
        (-1..1).each do |i|
            (-1..1).each do |j|
                c = { x: current[:x]+i, y: current[:y]+j }
                unless not_checked.include?(c) || checked.include?(c)
                    if get(map, c) == '#'
                        checked.push c
                    elsif get(map, c) == '?'
                        checked.push c
                        edges[current] = { cost: cost[current], move: direction[current] }
                    else
                        not_checked.unshift c

                        cost[c] = cost[current] + 1
                        if direction[current] == 9 # assign initial direction
                            direction[c] = DIRECTIONS.find_index([i,j])
                        else
                            direction[c] = direction[current]
                        end

                        if get(map, c) == 'o'
                            return direction[c], if cost[c] == 1 then 'N' else 'A' end
                        end

                        edges[c] = { cost: cost[c], move: direction[c] } if c[:x] == 0 || c[:x] == map[0].length - 1 ||
                                                                            c[:y] == 0 || c[:y] == map.length - 1
                    end
                end
            end
        end
    end

    # If no egg has been found return the move to the closest edge
    nearest_edge = edges.keys.sort_by { |c| edges[c][:cost] }.first
    if edges.length > 0
        return edges[nearest_edge][:move], 'A'
    else
        # The entire map has been scanned and no more eggs are left.
        # Wait for the game to end.
        return 9, 'N'
    end
end

input = $<.read.split "\n"
fov = input[0..4]
memory = input[5]

if memory
    map, coords = decode memory
    map, coords = update(map, fov, coords)
else
    map = fov
    coords = {x: 2, y: 2}
end
clean_up map

move, attack = scan_surroundings(map, coords)

memory = encode map, move_to(move, coords)

puts "#{move}
#{attack}
#{memory}"

이 봇은 이전에 본 것을 기억하고 매 차례마다 더 큰지도를 만들려고합니다. 그런 다음 가장 가까운 계란에 대한 너비 우선 검색을 사용하여 그렇게합니다. 현재 맵에 도달 할 수있는 에그가없는 경우, 봇은 맵의 가장 가까운 열린 가장자리로 향합니다 (맵은 여전히 ​​움직일 수있는 방향으로 빠르게 확장됩니다).

이 봇에는 아직 다른 봇 개념이 없으며 전투 전략도 없습니다. 이동이 성공적인지 판단 할 수있는 신뢰할만한 방법을 찾지 못했기 때문에 문제가 발생할 수 있습니다. 나는 항상 이동이 성공했다고 가정합니다. 따라서 새로운 패치가 아닌 경우 잘못된 위치에 맵에로드되어 경로 찾기에 해로울 수도 있고 그렇지 않을 수도 있습니다.

봇은 메모리를 사용하여 맵과 맵에 새 위치를 저장합니다 (이동이 성공적이라고 가정). 맵은 줄 바꿈없이 압축되고 base64로 인코딩되어 저장됩니다 (줄 바꿈을 다시 삽입 할 수 있도록 맵의 행 수와 함께). 이 압축은 압축되지 않은 맵의 약 3 분의 1로 크기를 줄이므로 1000 바이트가 넘는 음영을 가지면 약 3000 개의 셀 맵을 저장할 수 있습니다. 이는 대략 18 개의 봇이있는 맵을 탐색하는 것과 거의 같습니다. 많은 제출물에 가까운 곳이 없다면 그 사건에 대한 해결책을 찾기 위해 귀찮게 할 수 없다고 생각합니다.

5 dumbbot초 및 1 초 동안 몇 번의 테스트 실행 후naivebot (나의 다른 제출물) 실제로 1 ~ 2 개의 계란과 같은 성능이 좋지 않거나 다른 마진 (7 ~ 9 개의 계란)보다 성능이 뛰어납니다. 나는 더 나은 전투 전략과 내가 실제로 이사했는지 아닌지를 어떻게 결정할 수 있는지에 대해 생각할 수 있습니다. 둘 다 점수를 다소 향상시킬 수 있습니다.

아 그리고 봇의 이름이 궁금하다면 The Order of The Stick ( 이 만화의 마지막 패널)을 읽어보십시오 .

편집 : 발견 된지도의 가장자리를 감지하는 데 몇 가지 버그가있었습니다. 이제이 봇을 고쳤으므로이 봇은 항상 205 dumbbot초와 1 대 점수를 얻습니다 naivebot. 더 좋아! $stderr.puts map지금 내 봇에 추가 하면 그가 어떻게 체계적으로 맵을 발견하고 그 동안 모든 알을 수집하는지 알 수 있습니다. 또한 달걀을 밟지 않을 때마다 A대신 N봇의 원래 셀로 다시 이동할 가능성을 줄이기 위해 선택했습니다.

(6 naivebot초 에 비해 성능이 좋지 않습니다 . 특히 계란을 잡아서 선택하고 싶을 때 다른 봇과 함께 "교착 상태"로 끝나는 것이 가능하기 때문에 특히 그렇습니다 N. )


3

자바 토끼

이 토끼는 아직 자라지 않았지만 (여전히 변경을 계획하고 있음), 지금은 출발점입니다. 그는 가장 가까운 계란을 찾아 그것을 향해 간다. 벽면 감지 또는 범위를 벗어난 감지 (아직)는 없습니다. 그는 자신이 착륙 한 알을 집 으러 갈 것이다. 근처에 계란이 없으면 가장 가까운 토끼를 따라 가기 시작합니다. 그들은 그가 모르는 것을 알고있을 것입니다. 그렇지 않으면, 그는 걷는 임의의 방향을 선택할 것입니다. 그리고 그는 매우 잊어 버렸습니다 (메모리 변수를 사용하지 않음).

앞으로 계획 :

  • 벽 / 경계를 기반으로 의사 결정
  • 무작위가 아닌 목적으로 경로를 선택하십시오.
  • 메모리를 사용하여 내가 가고 있던 방향을 결정하십시오.

업데이트 1 내 토끼는 계란이 보이지 않으면 다른 토끼를 따라갑니다. 또한 "가장 가까운 계란 찾기"코드를 자체 방법으로 리팩토링했습니다.

import java.util.*;

public class EasterEggHunt {

    // board chars
    public static final char EGG = 'o';
    public static final char WALL = '#';
    public static final char BUNNY = '*';
    public static final char SPACE = ' ';
    public static final char OUT_OF_BOUNDS = 'X';

    // player moves
    public static final char ATTACK = 'A';
    public static final char COUNTER = 'C';
    public static final char NOTHING = 'N';

    // directions
    public static final int UPPER_LEFT = 1;
    public static final int UP = 2;
    public static final int UPPER_RIGHT = 3;
    public static final int RIGHT = 4;
    public static final int LOWER_RIGHT = 5;
    public static final int DOWN = 6;
    public static final int LOWER_LEFT = 7;
    public static final int LEFT = 8;
    public static final int STAY = 9;


    // the size of the immediate area
    // (I'll be at the center)
    public static final int VISION_RANGE = 5;

    public static void main(String[] args) {

        Scanner input = new Scanner(System.in);

        char[][] immediateArea = new char[VISION_RANGE][VISION_RANGE];

        for (int i = 0; i < VISION_RANGE; ++i) {
            String line = input.nextLine();
            for (int j = 0; j < VISION_RANGE; ++j) {
                immediateArea[i][j] = line.charAt(j);
            }
        }

        String memory = input.nextLine();

        int moveDirection = decideMoveDirection(immediateArea, memory);
        System.out.println(moveDirection);

        char action = decideAction(immediateArea, memory, moveDirection);
        System.out.println(action);

        // change the memory?
        System.out.println(memory);

    }

    private static int decideMoveDirection(char[][] immediateArea, String memory) {

        // if there's a nearby egg, go towards it
        int direction = nearestBoardObject(immediateArea, EGG);

        // if we didn't find an egg, look for a bunny
        // (maybe he knows where to find eggs)
        if (direction == STAY)
            direction = nearestBoardObject(immediateArea, BUNNY);

        // otherwise, pick a random direction and go
        // we want to also have the chance to stop and catch our breath
        if (direction == STAY)
            direction = new Random().nextInt(STAY + 1);

        return direction;
    }

    private static int nearestBoardObject(char[][] immediateArea, char boardObject) {

        // start at the center and go outward (pick a closer target over a farther one)
        int spacesAway = 1;
        int meX = immediateArea.length / 2;
        int meY = immediateArea[meX].length / 2;

        while (spacesAway <= immediateArea.length / 2) {

            // I like to look right, and go clockwise
            if (immediateArea[meX][meY + spacesAway] == boardObject)
                return RIGHT;
            if (immediateArea[meX + spacesAway][meY + spacesAway] == boardObject)
                return LOWER_RIGHT;
            if (immediateArea[meX + spacesAway][meY] == boardObject)
                return DOWN;
            if (immediateArea[meX + spacesAway][meY - spacesAway] == boardObject)
                return LOWER_LEFT;
            if (immediateArea[meX][meY - spacesAway] == boardObject)
                return LEFT;
            if (immediateArea[meX - spacesAway][meY - spacesAway] == boardObject)
                return UPPER_LEFT;
            if (immediateArea[meX - spacesAway][meY] == boardObject)
                return UP;
            if (immediateArea[meX - spacesAway][meY + spacesAway] == boardObject)
                return UPPER_RIGHT;

            ++spacesAway;
        }

        // if the target object isn't in the immediate area, stay put
        return STAY;

    }

    private static char decideAction(char[][] immediateArea, String memory, int moveDirection) {

        char destinationObject = getDestinationObject(immediateArea, moveDirection);

        switch (destinationObject) {

            case EGG:
                // don't break the egg
                return NOTHING;
            default:
                // get really aggressive on everything else
                // other players, walls, doesn't matter
                return ATTACK;

        }

    }

    private static char getDestinationObject(char[][] immediateArea, int moveDirection) {

        // start at my spot (middle of the board) and figure out which direction I'm going
        int targetX = immediateArea.length / 2;
        int targetY = immediateArea[targetX].length / 2;

        switch (moveDirection) {

            case RIGHT:
                ++targetY;
                break;
            case LOWER_RIGHT:
                ++targetX;
                ++targetY;
                break;
            case DOWN:
                ++targetX;
                break;
            case LOWER_LEFT:
                ++targetX;
                --targetY;
                break;
            case LEFT:
                --targetY;
                break;
            case UPPER_LEFT:
                --targetX;
                --targetY;
                break;
            case UP:
                --targetX;
                break;
            case UPPER_RIGHT:
                --targetX;
                ++targetY;
                break;
            // otherwise we aren't moving

        }

        return immediateArea[targetX][targetY];

    }

}

또한 Java 열거 형이 클래스에 거의 가득 차 있다는 것을 알게되었으며 .NET 열거 형이 훨씬 좋습니다.
Brian J

0

NaiveBot (루비)

다음은 계란 롤링을 얻는 매우 단순한 봇입니다 (우리는이 7 개의 제출물을 빨리 치고 싶습니다). 내 루비는 관용적이지 않으므로이 코드는 적절한 루비리스트가 고통에 빠지게 할 수 있습니다. 자신의 책임하에 읽으십시오.

input = $<.read
$data = input.split("\n")

def is_egg x, y
    $data[y+2][x+2] == 'o'
end

def is_wall x, y
    $data[y+2][x+2] == '#'
end

def is_empty x, y
    $data[y+2][x+2] == ' '
end

def is_player x, y
    $data[y+2][x+2] == '*'
end

if (is_egg(-2,-2) || is_egg(-2,-1) || is_egg(-1,-2)) && !is_wall(-1,-1) || is_egg(-1,-1)
    dir = 1
elsif is_egg(0,-2) && !is_wall(0,-1) || is_egg(0,-1)
    dir = 2
elsif (is_egg(2,-2) || is_egg(2,-1) || is_egg(1,-2)) && !is_wall(1,-1) || is_egg(1,-1)
    dir = 3
elsif is_egg(2,0) && !is_wall(1,0) || is_egg(1,0)
    dir = 4
elsif (is_egg(2,2) || is_egg(2,1) || is_egg(1,2)) && !is_wall(1,1) || is_egg(1,1)
    dir = 5
elsif is_egg(0,2) && !is_wall(0,1) || is_egg(0,1)
    dir = 6
elsif (is_egg(-2,2) || is_egg(-2,1) || is_egg(-1,2)) && !is_wall(-1,1) || is_egg(-1,1)
    dir = 7
elsif is_egg(-2,0) && !is_wall(-1,0) || is_egg(-1,0)
    dir = 8
else
    dir = rand(8) + 1
end

attack = 'N'
puts "#{dir}
#{attack}
"

로 실행하십시오 ruby naivebot.rb.

난 그냥 계란이 보이는 벽에 의해 방해받지 않는 몇 가지 경우를 하드 코딩하고 있습니다. 가장 가까운 계란은 가지 않지만 첫 번째 움직임을 선택합니다. 그러한 알을 찾지 못하면 봇은 무작위로 움직입니다. 그것은 다른 모든 플레이어를 무시하고 공격하거나 카운터하지 않습니다.


0

WallFolower

파이썬 3 에서 (장려하다) :

import sys
import random

#functions I will use
dist       = lambda p1,p2: max(abs(p2[1] - p1[1]), abs(p2[0] - p1[0]))
distTo     = lambda p    : dist((2,2), p)
cmp        = lambda x,y  : (x > y) - (x < y)
sgn        = lambda x    : (-1,0,1)[(x>0)+(x>=0)]
move       = lambda p    : (sgn(p[0] - 2), sgn(p[1] - 2))
unmove     = lambda p    : (p[0] * 2 + 2, p[1] * 2 + 2)
outputmove = lambda p    : (1,2,3,8,9,4,7,6,5)[(sgn(p[0] - 2) + 1) + 3*(sgn(p[1]-2) + 1)]
def noeggfinish(move):
    print(outputmove(unmove(move)))
    print('ACN'[random.randint(0, 2)])
    print("1"+move)
    sys.exit(0)

#beginning of main body
view    = [list(l) for l in map(input, ('',)*5)] #5 line input, all at once.
memory  = input() #currently used only as last direction moved in a tuple
eggs    = []
enemies = []
for y in range(5):
    for x in range(5):
        if   view[y][x] == 'o': eggs    += [(x,y)]
        elif view[y][x] == '*': enemies += [(x,y)]

eggs.sort(key = lambda p:distTo(p)) #sort by how close to me they are.

tiedeggs = []
end = 0
for egg in eggs[:]:
    if end:break
    for enemy in enemies:
        exec({
            -1: 'eggs.remove(egg)',
             0: 'tiedeggs += egg',
             1: 'end=1'
        }[cmp(dist(enemy, egg), distTo(egg))])
        if end:break
if eggs:
    print(outputmove(eggs[0]))
    print('N')              #no attack here
    print("0"+move(eggs[0]))
    sys.exit(0)
elif tiedeggs:
    print(outputmove(tiedeggs[0]))
    print('N')              #no attack here
    print("0"+move(tiedeggs[0]))
    sys.exit(0) 
#now there are no eggs worth going for
#do a LH wall follow

lastmove = eval(memory[1:]) #used to resolve ambiguity
if lastmove[0] and lastmove[1]:
    lastmove[random.randint(0,1)] = 0 #disregard diagonal moves
if eval(memory[0]):
    exec("check=view[%n][%n]"%{(0,-1):(0,0),(1,0):(4,0),(0,1):(4,4),(-1,0):(0,4)}[lastmove])
    if check == '#':
        noeggfinish(lastmove)
    else:pass
#currently unimplemented
#move randomly
noeggfinish(tuple([(x,y) for x in [-1,0,1] for y in [-1,0,1] if (x,y) != (0,0)))

계란이 보이는 경우 다른 로봇보다 계란에 더 가까운 경우에만 계란으로 이동합니다. 먼 거리에 넥타이가 있으면 어쨌든갑니다. 그렇지 않으면 LH 벽이 따라갑니다 (현재는 잘 구현되지 않았습니다).

여전히 벽을 따라 작업해야하지만 어쨌든 여기에 게시하겠습니다.


1
tester.py로 봇을 실행하면 콘솔에 다음 오류가 발생합니다. pastebin.com/cT5xGdSW
starbeamrainbowlabs

여기도 마찬가지입니다. 당신은 그것을 볼 수 있습니까? 새 봇을 테스트하고 싶습니다.
Martin Ender

당신이 변경하면 @ m.buettner 어떻게됩니까 sys.exit(0)exit(0)? 또한이 작업을 수행해야합니다 (지금은 자체가``라고 가정)하지만 실제로 시간이 없습니다. 시간이 있으면 와서 고칠거야.
저스틴

@Quincunx 불행히도, 그것은 아무것도 바뀌지 않았습니다.
Martin Ender
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.