지뢰 찾기 보드 반전


32

지뢰 찾기 는 인기있는 컴퓨터 게임으로, 각각의 비광 셀이 몇 개의 주변 광산을 가지고 있는지에 대한 힌트를 바탕으로 직사각형 그리드에서 광산 인 셀을 표시하려고 할 때 시간을 낭비했을 것입니다. 그리고 당신이 그것을 연주하지 않은 경우, 여기 에서 연주 하십시오 .

지뢰 찾기 그리드 (일명 보드)에 대한 멋진 수학적 사실은 다음과 같습니다.

보드와 그 보완 물은 동일한 총 광산 수를 갖습니다 . ( 증거 )

즉,이 경우 완전히 지뢰 찾기 그리드를 공개한다는 말을하는 것입니다, 합이 그리드에 모든 숫자, 즉 광산 전체 의 모든 광산을 교체 그리드는 그리드의 보수의 광산 전체를 동일합니다, 비 광산으로, 모든 비 광산은 광산으로 대체되었습니다.

예를 들어 지뢰 찾기 표의 경우

**1..
34321
*2**1

광산 총계는 1 + 3 + 4 + 3 + 2 + 1 + 2 + 1 = 17입니다.

그리드의 보완은

24***
*****
3*44*

내 총계가 2 + 4 + 3 + 4 + 4 = 17입니다.

지뢰를 *나타내는 텍스트 형식으로 임의의 지뢰 찾기 그리드를 사용하는 프로그램을 작성하십시오 . 비 광산 셀에 인접한 지뢰 수 18나타냅니다. 당신은 사용할 수 있습니다 .또는 0또는 (공간)없는 내 이웃, 당신의 선택에 세포를 나타냅니다. 입력 그리드가 올바르게 표시되어 있다고 가정 할 수 있습니다. 즉, 각각의 비광 셀은 직교 또는 대각선으로 바로 인접한 총 광산 수를 정확하게 나타냅니다.

프로그램이 동일한 형식으로 그리드의 보수를 인쇄 할 필요가있다 (같은를 사용하여 ., 0또는 당신이 입력에서 예상대로).

바이트 단위의 가장 짧은 코드가 이깁니다.

  • 프로그램 대신 입력 그리드를 문자열로 가져와 보완 그리드를 인쇄하거나 반환하는 함수를 작성할 수 있습니다.
  • 입력 또는 출력의 후행 줄 바꿈은 좋지만 그리드를 형성하는 문자 외에 다른 문자는 없어야합니다.
  • 1 × 1 격자가 가장 작은 입력이라고 가정 할 수 있습니다.

테스트 사례

보수의 보수가 원래 그리드이므로 모든 입력 및 출력을 교환 할 수 있습니다. 추가 테스트 사례를 위해 그리드를 회전 할 수도 있습니다.

입력:

111
1*1
111

산출:

***
*8*
***

입력:

.

산출:

*

입력:

*11*1.1**1...1***1.....1*****1..........

산출:

1**2***11*****1.1*******1...1***********

입력 : ( 컷 매듭 예제 )

**212*32
333*33**
1*22*333
222222*1
*33*2232
2**22*2*

산출:

24***4**
***7**64
*8**7***
******8*
4**7****
*33**5*3

TI-BASIC은 빈 줄을 입력 할 수 없습니다. ?보드의 마지막 줄 다음에 줄에 끝 구분 기호 (예 :)를 사용할 수 있습니까?
lirtosiast

@ThomasKwa TI-BASIC 및 줄 바꿈 제한이 이상한 다른 언어에는 끝 구분 기호가 적합합니다.
Calvin 's Hobbies

답변:


12

Pyth, 39 38 바이트

j.es.eh-+K\*l-s:RtWYY+Y2:+K.zk+k3KZb.z

온라인으로 사용해보십시오 : 데모

주요 알고리즘은 정말 간단합니다. 나는 단순히 각 셀을 반복하고 주변의 3x3 상자 (또는 셀이 경계에있을 때 더 작음)를 가져 와서 해당 상자에 별 또는 별이 아닌 수를 인쇄합니다.

설명:

j.es.eh-+K\*l-s:RtWYY+Y2:+K.zk+k3KZb.z  implicit: .z = list of input strings
 .e                                 .z  map each index k, line b of .z to:
    .e                             b      map each index Y, char Z of b to:
         K\*                                assign "*" to K
                         +K.z               insert K at the front of .z
                        :    k+k3           slice from k to k+3
               :RtWYY+Y2                    take the slice from Y-1 or 0 
                                            to Y+2 for each line
              s                             join, this gives the 3x3 rectangle
                                             (or smaller on the border)
             -                   K          remove all "*"s
            l                               take the length
        +K                                   "*" + ^
       -                          Z         remove Z from this string
      h                                     and take the first char
                                            (if cell=mine take the number, 
                                             otherwise take the number)
  s                                       join the chars of one line
j                                       join by newlines

정말 깔끔합니다, +1
MKII September

22

CJam, 58 57 바이트

0WX]2m*qN/{'*f+z}2*f{\~@m<fm<W<}:..+{W<{_'*#'*@'*-,?}/N}/

입력은 줄 바꿈으로 끝나서는 안됩니다. 0근처에 광산이없는 셀 에 대한 출력이 포함 됩니다.

CJam 통역사 에서 온라인으로 사용해보십시오 .

생각

입력 행렬을 한 행과 한 열의 별표로 채우는 것으로 시작합니다.

입력

*4*
**2

이 결과

*4**
**2*
****

이제 행과 열을 0, -1 또는 1 단위 위 / 왼쪽으로 회전하여 가능한 모든 수정 사항을 생성합니다.

*4** **** **2* **4* **** ***2 4*** **** *2**
**2* *4** **** ***2 **4* **** *2** 4*** ****
**** **2* *4** **** ***2 **4* **** *2** 4***

각 회전에서 "패딩 위치"를 버립니다. 즉,

*4* *** **2 **4 *** *** 4** *** *2*
**2 *4* *** *** **4 *** *2* 4** ***

각 회전의 해당 문자를 연결하여 단일 행렬을 형성하십시오.

******4** 4*******2 **24*****
*******4* *4****2** 2***4****

각 위치의 첫 번째 문자는 원래 문자입니다.

  • 별표가 아닌 경우 별표로 바꿔야합니다.

  • 별표 인 경우 해당 문자열의 비 별표 수는 주변 광산의 수입니다.

작동 원리

0WX]2m*   e# Push the array of all vectors of {0,-1,1}^2.
qN/       e# Read all input from STDIN and split at linefeeds.
{'*f+z}2* e# Append a '*' to each row and transpose rows with columns. Repeat.
f{        e# For each vector [A B], push the modified input Q; then:
  \~      e#   Swap Q with [A B] and dump A and B on the stack.
  @m<     e#   Rotate the rows of Q B units up.
  fm<     e#   Rotate each row of the result A units left.
  W<      e#   Discard the last row.
}         e# This pushes all nine rotations with Manhattan distance 1.
:..+      e# Concatenate the corresponding characters for each position.
{         e# For each row:
  W<      e#   Discard the character corresponding to the last column.
  {       e#   For each remaining string:
    _'*#  e#     Find the first index of '*' in a copy.
    '*    e#     Push '*'.
    @'*-, e#     Count the non-asterisks in the string.
    ?     e#     Select '*' if the index is non-zero, the count otherwise.
  }/      e#
  N       e#   Push a linefeed.
}/        e#

7
나는 두려운 다 – 이것은 훌륭하다.
Deusovi

당신은 시스템을 깨뜨 렸습니다. +1! 이 이론을 어디서 찾았는지 물어봐도 될까요?
GamrCorps

9
@IonLee이 사람은 모두 나입니다. 정말 간단한 아이디어입니다. 주어진 셀 주위의 셀을 확인하는 대신 전체 그리드를 이동하고 셀에 떨어지는 것을 관찰합니다.
Dennis

브라보! 나는 그런 생각을하지 않았다.
GamrCorps

7

루비, 119

->s{w=1+s.index('
')
s.size.times{|c|t=0;9.times{|i|(s+?**w*2)[c+i/3*w-w+i%3-1]<?0||t+=1}
print [t,?*,'
'][s[c]<=>?*]}}

테스트 프로그램에서 ungolfed :

f=->s{
  w=1+s.index("\n")                          #width of board
  s.size.times{|c|                           #iterate through input
    t=0;                                     #number of digits surrounding current cell
    9.times{|i|                              #iterate through 3x3 box (centre must be * if this ever gets printed.)
      (s+"*"*w*2)[c+i/3*w-w+i%3-1]<"0"||t+=1 #copy of s has plenty of * appended to avoid index errors
    }                                        #add 1 every time a number is found.
  print [t,"*","\n"][s[c]<=>"*"]             #if * print t. if after * in ACSII it's a number, print *. if before, it's \n, print \n
  }
}


f['**212*32
333*33**
1*22*333
222222*1
*33*2232
2**22*2*']

2

옥타브, 76

m=@(s)char(conv2(b=(cell2mat(strsplit(s)'))~='*',ones(3),'same').*~b-6*b+48)

설명

  • 변환 입력 문자열하여 문자열의 매트릭스 strsplitcell2mat.

  • 원래 행렬에 1없는 곳에 포함 된 논리 행렬 *을 가져옵니다.

  • 1의 3x3 행렬로 컨볼 루션을 수행하십시오.

  • 역 논리 행렬로 *마스크를 마스크하고 마스크를 대신합니다.

  • 참고 : 내 이웃이없는 셀은로 표시됩니다 0.

실행

>> m(['**100' 10 '34321' 10 '*2**1'])   %// `10` is newline
ans =

24***
*****
3*44*

>> m(['24***' 10 '*****' 10 '3*44*'])
ans =

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