내 여행을 시원하게 유지하십시오!


11

도전

Marks and Spencers를 돌아 다니면서 상점 주변에 에어컨 장치가 무작위로 배치 된 것을 발견했습니다. 시원하게 유지하고 싶을 때 에어컨 장치에서 너무 오랫동안 떨어져 있지 않고 상점 전체를 돌아 다니는 가장 쉬운 방법이 무엇인지 궁금했습니다.

지도가 주어지면 에어컨 장치와의 거리를 가능한 짧게 유지하면서 (AC 장치가 벽의 다른쪽에 있더라도) 전체지도를 돌아 다니는 방법을 찾아야합니다.

지도

지도는 원하는 방식으로 제공 될 수 있으며 다음 기호를 사용합니다.

+ is a corner of a wall
| is a east/west facing wall
- is a north/south facing wall
X is an air conditioning unit
S is the start and end point

예제 맵은 다음과 같습니다.

+------S---+
|   X      |
| ---+-+ X |
|    |X|   |
| ---+ +---+
|   X      |
+----------+

또는

+---+--+
| X |  |
|   |  +-----+------+
|   | X      | X    |
|     ---+       |  S
|   |    |  X    |  |
|   |  +-+-------+--+
| X    |
+------+

전체지도를 여행한다는 것은 모든 빈 공간과 에어컨을 통과한다는 의미입니다. 벽을 통과 할 수 없으며 직각으로 만 이동할 수 있습니다. 지도가 항상 직사각형 인 것은 아닙니다.

AC 장치와의 거리를 최대한 짧게 유지하는 것이 모든 시간 간격의 합입니다.

통과는 출입을 의미합니다.

원하는 방식으로 경로를 출력 할 수 있습니다. 예를 들면 다음과 같습니다.

  • 경로가 포함 된 맵 출력
  • (예를 들어 나침반 포인트 연속적으로 출력 경로 NNSESW)

2
@BetaDecay 그리고 그것은 어떻게 계산됩니까? 어느 시점에서 최대 거리? 모든 시간 간격에 대한 거리의 합 / 평균?
Ingo Bürk

5
이 문제의 목표가 무엇인지 이해하는 것은 불가능합니다. 모든 광장을 방문 해야하는 경우 최대 거리는 일정합니다.
feersum

1
@feersum 왜 그렇습니까? 지도 레이아웃으로 특정 사각형을 다시 방문해야하므로 경로 지정에 여러 가능성을 부여 할 수 없습니까?
InvisiblePanda

6
이것이 최적화 문제입니까? 그렇지 않은 경우 올바른 출력을 가진 일부 테스트 사례가 있어야합니다.
mbomb007

2
첫 번째 예에서 유일하게 두 가지 가능한 주행 거리를 제공 할 수 있습니까?
mdahmoune

답변:


1

WindowsPowerShell , 376 367 바이트

게으른 사람처럼 모든 선반에 가지 않고 상점의 에어컨에서 에어컨으로 옮깁니다. 나는 모든 에어컨을 방문하는 가게 전체를 여행했다고 생각합니다.

$f={param($m,$d,$o=@{})$w=(($l=$m-split"
")|% le*|sort)[-1]
$m=($l|% *ht $w)-join"
"
if(!$o.$m-or$o.$m-ge$d-and$m-match'(?s)X.*S|S.*X'){$o.$m=$d++
$n=-split")X(S )X(.{$w}S S)X( S.{$w})X("|%{sls "(?s)^(.*$_.*)$" -inp $m -a|% m*|%{($_.Groups-replace'S',' ')[1,2]-join'S'}}
$d=(($n+,($m-replace"(?s)(?<=S(.{$w})?) | (?=(.{$w})?S)",'S')*!$n)|%{&$f $_ $d $o}|sort)[0]}+$d}

온라인으로 사용해보십시오!

풀림 :

$f={
    param($map,$distance,$o=@{})
    $lines = $map-split"`n"
    $width = ($lines|% length|sort)[-1]
    $map = ($lines|% padRight $width)-join"`n"                              # to rectangle

    if(!$o.$map -or $o.$map-ge$distance -and $map-match'(?s)X.*S|S.*X'){
        $o.$map = $distance++                                               # store a map to avoid recalculations
        $n = -split")X(S )X(.{$width}S S)X( S.{$width})X("|%{               # search a nearest X in 4 directions
            select-string "(?s)^(.*$_.*)$" -InputObject $map -AllMatches|% Matches|%{
                ($_.Groups-replace'S',' ')[1,2]-join'S'                     # start a new segment (reset all S and replace the nearest X by S)
            }
        }
        $stepMore = $map-replace"(?s)(?<=S(.{$w})?) | (?=(.{$w})?S)",'S'
        $n += ,$stepMore*!$n                                                # add a step if X was not found
        $distance=($n|%{&$f $_ $distance $o}|sort)[0]                       # recursive repeat
    }

    +$distance
}
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.