매트릭스 토네이도 조심!


27

매트릭스 토네이도는 다른 토네이도와 마찬가지로 중심을 중심으로 회전하는 물체로 구성됩니다. 이 경우 공기 대신 매트릭스의 요소입니다.

다음은 토네이도 행렬의 예입니다.

작동중인 매트릭스 토네이도

먼저 행렬을 정사각형 고리로 나누는 것으로 시작합니다. 각 섹션은 같은 거리만큼 경계에서 멀리 떨어진 요소로 구성됩니다. 이 부분들은 중앙을 중심으로 시계 방향으로 회전합니다. 실제 토네이도에서는 중심쪽으로 갈수록 심각도가 증가하고 매트릭스 토네이도에서 회전 단계도 증가합니다. 가장 바깥 쪽 섹션 (빨간색 섹션)은 1 단계 회전하고 다음 (노란색) 섹션은 2 회전합니다. 에. 회전 단계는 중심을 중심으로 90 ° 회전하는 것입니다.

태스크:

당신이해야 할 일은 사각형 행렬을 입력으로 받아 함수에 프로그램을 작성하고 토네이도 효과를 적용한 다음 결과 행렬을 출력하는 것입니다.

입력:

입력은 n여기서 정방형 행렬이어야합니다 n >= 1. 행렬의 요소에 대해 가정하지 않아도됩니다.

산출:

입력 행렬에 트로 나도 효과를 적용한 결과와 동일한 순서의 정사각 행렬.

예 :

순서의 행렬 n = 1:

[['Hello']]               ===>    [['Hello']]

순서의 행렬 n = 2:

[[1 , 2],                 ===>    [[5 , 1],
 [5 , 0]]                          [0 , 2]]

순서의 행렬 n = 5:

[[A , B , C , D , E],             [[+ , 6 , 1 , F , A],
 [F , G , H , I , J],              [- , 9 , 8 , 7 , B],
 [1 , 2 , 3 , 4 , 5],     ===>     [/ , 4 , 3 , 2 , C],
 [6 , 7 , 8 , 9 , 0],              [* , I , H , G , D],
 [+ , - , / , * , %]]              [% , 0 , 5 , J , E]]

회전이 90 ° 회전임을 명확히하고 싶다고 생각합니다.
Outgolfer Erik

또한, 당신은 다른 곳에서이 도전을 받아들였습니까? 그렇다면 귀속을 제공해야합니다.
Outgolfer Erik

1
@EriktheOutgolfer 1) 나는 그것을 분명히했습니다. 2)이 도전은 나의 것이다.
ibrahim mahrir

4
@Giuseppe 어느 반구에 있는지에 따라 다릅니다.;)
Jo King

12
먼저 이것이 좋은 도전이라고 생각합니다 : 좋은 일입니다! 하지만 플러그인 좋아도 좋겠 내가 당신의 선택은 모든 유형의 데이터가 어색한 자리에 당신의 도전을 잎이 될 수 있다고 생각하기 때문에 포인트. 입력 목록에 대한 설명과 마찬가지로 오버 헤드 작업을 수행하지 않고이 문제를 해결할 수있는 언어를 제한했습니다. 이러한 요구 사항이 완화되면 문제가 더 낫다고 생각합니다. 이와 같은 멋진 도전을 계속 게시하기를 바랍니다. :)
FryAmTheEggman

답변:


5

파이썬 3 , 100 바이트

import numpy
def f(a):
 if len(a): a=numpy.rot90(a,axes=(1,0));a[1:-1,1:-1]=f(a[1:-1,1:-1]);return a

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


8
고전적인 파이썬, a[1:-1,1:-1]=f(a[1:-1,1:-1])2 차원 배열의 전체를 직접 가져 와서 설정하는 것이 세상에서 가장 일반적인 것처럼 떨어지는 것
ETHproductions

1
@ETHproductions 공정하게 말하면, 그것의 일부는 다음에서 상속 된 구문입니다.numpy
Jo King

1
numpy.rot90(a,1,(1,0))3 바이트 짧아지고 작동해야합니다.
Graipher

1
? 어떤 어떤 테스트 케이스없이 TIO-링크의 포인트는 ...입니다 : S 가 함께 여기 (에 공간을 떨어 if len(a):a=...-1 바이트).
Kevin Cruijssen '

5

, 44 바이트

≔EθSθWθ«≔Eθ⮌⭆觧θνλθθM¹⁻¹Lθ≔E✂θ¹±¹¦¹✂κ¹±¹¦¹θ

온라인으로 사용해보십시오! 링크는 자세한 버전의 코드입니다. Charcoal의 기본 I / O는 일반적인 배열 정의를 수행하지 않기 때문에 문자 사각형에서만 작동합니다. 설명:

≔EθSθ

문자 사각형을 읽으십시오.

Wθ«

비어있을 때까지 반복하십시오.

≔Eθ⮌⭆觧θνλθ

회전 시키십시오.

θM¹⁻¹Lθ

인쇄 한 다음 커서를 원래 모서리에서 대각선으로 한 정사각형으로 이동하십시오.

≔E✂θ¹±¹¦¹✂κ¹±¹¦¹θ

배열에서 바깥 쪽을 자릅니다.


5

젤리 , 27 바이트

J«þ`UṚ«Ɗ‘ịZU$LСŒĖḢŒHEƊƇṁµG

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

나는 이것이 훨씬 짧을 수 있다고 생각합니다.

           Input: n×n matrix A.
J          Get [1..n].
 «þ`       Table of min(x, y).
    UṚ«Ɗ   min with its 180° rotation.

Now we have a matrix like: 1 1 1 1 1
                           1 2 2 2 1
                           1 2 3 2 1
                           1 2 2 2 1
                           1 1 1 1 1

‘ị          Increment all, and use as indices into...
     LС    List of [A, f(A), f(f(A)), …, f^n(A)]
  ZU$       where f = rotate 90°

Now we have a 4D array (a 2D array of 2D arrays).
We wish to extract the [i,j]th element from the [i,j]th array.

ŒĖ     Multidimensional enumerate

This gives us: [[[1,1,1,1],X],
                [[1,1,1,2],Y],
                ...,
                [[n,n,n,n],Z]]

ḢŒHEƊƇ     Keep elements whose Ḣead (the index) split into equal halves (ŒH)
           has the halves Equal to one another. i.e. indices of form [i,j,i,j]
           (Also, the head is POPPED from each pair, so now only [X] [Y] etc remain.)

ṁµG        Shape this like the input and format it in a grid.

1
당신은 아마 µG바닥 글에 넣고 제출이 25라고 주장 할 수 있습니다.
Mr. Xcoder

5

펄 6 , 78 73 72 바이트

-5 바이트의 nwellnhof에 감사합니다!

$!={my@a;{(@a=[RZ] rotor @_: sqrt @_)[1..*-2;1..@a-2].=$!}if @_;@a[*;*]}

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

평평한 2D 배열을 사용하고 유사하게 평평한 배열을 반환하는 재귀 코드 블록입니다.

설명:

$!={      # Assign code block to pre-declared variable $!
    my@a; # Create local array variable a
   {
     (@a=[RZ]  # Transpose:
             rotor @_: sqrt @_;  # The input array converted to a square matrix
     )[1..*-2;1..@a-2].=$!  # And recursively call the function on the inside of the array
   }if @_;    # But only do all this if the input matrix is not empty
   @a[*;*]  # Return the flattened array
}

배열을 평평하게하는 @a[*;*]대신 사용할 수 있습니다 map |*,@a. (
평면화

그러나 @a[1..*-2;1..@a-2].=$!작동합니다.
nwellnhof

5

옥타브 , 86 81 바이트

f(f=@(g)@(M,v=length(M))rot90({@(){M(z,z)=g(g)(M(z=2:v-1,z)),M}{2},M}{1+~v}(),3))

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

재귀 익명 함수는 Octave에서 작업을 수행하는 가장 짧은 방법은 아니지만 지금까지 가장 재미있는 방법 이라는 것을 알고 있습니다. 이것은 내가 얻을 수있는 가장 짧은 익명 함수이지만, 나는 outgolfed되고 싶습니다.

설명

재귀 함수는 ceilingcat 의이 답변에 따라 정의됩니다 . 재귀 호출 q=f(f=@(g)@(M) ... g(g)(M) ...과 같은 익명 함수의 기본 구조입니다 g(g)(M). 이것은 무한정 재귀되기 때문에 재귀 호출을 조건부 셀 배열로 래핑합니다 {@()g(g)(M),M}{condition}(). 빈 인수 목록을 가진 익명 함수는 조건이 선택된 후에 평가를 지연시킵니다 (하지만 나중에 인수 목록을 사용하여 정의 할 수 있음을 알 수 있습니다 z). 지금까지는 기본적인 부기였습니다.

이제 실제 작업하십시오. 함수 는 M의 중앙 부분에서 재귀 적으로 호출 된 rot90(P,-1)행렬을 P와 함께 반환하기를 원합니다 g(g). 우리는 M z=2:end-1의 색인에서 숨길 수있는 설정으로 시작합니다 . 이렇게 M(z,z)하면 행렬의 중앙 부분이 선택됩니다. 재귀 호출로 더 토네이도. 이 ,3부품은 회전이 시계 방향으로 이루어 지도록합니다. 남반구에 거주하는 경우이 비트를 -2 바이트 동안 제거 할 수 있습니다.

우리는 그렇습니다 M(z,z)=g(g)M(z,z). 그러나이 연산의 결과 값은 전체 P행렬이 아닌 수정 된 중앙 부분 입니다. 따라서 우리는 Stewie Griffin 의이 답변 {M(z,z)=g(g)M(z,z),M}{2}에서 기본적으로 도난당한 작업 을 수행 합니다.

마지막으로 condition입력이 비어 있으면 재귀가 중지됩니다.


남반구에 +1
ceilingcat

나는 그것을 시도를 제공하지 않도록, 아직 익명 함수의 재귀 주위에 내 머리를 정리 시도하지 않은,하지만 재귀 루프보다 짧은 경우 나는 궁금 해요 이있는 하나의 .
Stewie Griffin

@StewieGriffin 나는 내가 무엇을 할 수 있는지 볼 것이다 :)
Sanchises

@StewieGriffin 그런데 옥타브에서는 루프 기반 버전을이 챌린지에 게시해야한다는 부담을 느끼십시오. 재귀 적 접근법을 이길 수 있는지 정말로 궁금합니다.
Sanchises

4

아르 자형 , 87 바이트

function(m,n=nrow(m)){for(i in seq(l=n%/%2))m[j,j]=t(apply(m[j<-i:(n-i+1),j],2,rev));m}

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



허용 되나요? 이미지는 시계 방향 화살표와 아래 설명은 시계 방향 회전을 나타냅니다 ...
digEmAll

나는 질문을 열 번 읽었어야하고 시계 방향 (따라서 내 의견)이라고 말하는 것을 보지 않아야합니다. 아아.
주세페

Eheh, 그것에 대해 말해 ... 나는 오해 게시물의 왕입니다 : D
digEmAll

1
불행히도 1x1 행렬은 작동하지 않습니다 ( seq(0.5)빈 벡터 대신 1을 반환 하기 때문에 )
digEmAll

4

MATL , 25 24 23 22

t"tX@Jyq-ht3$)3X!7Mt&(

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

MATL에서의 인덱싱은 결코 쉽지 않지만 일부 골프에서는 실제로 현재 최고의 Jelly 답변을 능가합니다 ...

t                       % Take input implicitly, duplicate.  
 "                      % Loop over the columns of the input*
   X@                   % Push iteration index, starting with 0. Indicates the start of the indexing range.
     Jyq-               % Push 1i-k+1 with k the iteration index. Indicates the end of the indexing range
         t              % Duplicate for 2-dimensional indexing.
  t       3$)           % Index into a copy of the matrix. In each loop, the indexing range gets smaller
             3X!        % Rotate by 270 degrees anti-clockwise
                7Mt&(   % Paste the result back into the original matrix. 

* n x n행렬의 경우이 프로그램은 n반복을 수행하지만 실제로 n/2회전 만 필요 합니다. 그러나, MATL (AB)에서의 인덱싱은 인덱싱 불가능 범위가 단지 no-op 일 정도로 충분히 유연하다. 이런 식으로, 반복 횟수를 정확하게 얻기 위해 바이트를 낭비 할 필요가 없습니다.



3

K (ngn / k) , 41 39 38 바이트

{s#(+,/'4(+|:)\x)@'4!1+i&|i:&/!s:2##x}

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

{ } 인수 기능 x

#xlength- x행렬의 높이

2##x 두 부-높이와 너비 (동일한 것으로 가정)

s:s"모양"에 할당

!s형상의 행렬의 모든 인덱스는 s, 예를 들면 !5 5

(0 0 0 0 0 1 1 1 1 1 2 2 2 2 2 3 3 3 3 3 4 4 4 4 4
 0 1 2 3 4 0 1 2 3 4 0 1 2 3 4 0 1 2 3 4 0 1 2 3 4)

이것은 2 행 행렬 (목록 목록)이며 열은 5x5 행렬의 색인에 해당합니다.

&/ 두 행 이상 최소 :

0 0 0 0 0 0 1 1 1 1 0 1 2 2 2 0 1 2 3 3 0 1 2 3 4

i&|i:에 대입 i, 반전 ( |) 및 최소값 ( &)i

0 0 0 0 0 0 1 1 1 0 0 1 2 1 0 0 1 1 1 0 0 0 0 0 0

다음은 5x5 매트릭스의 평평한 고리 번호입니다.

4!1+ 1을 더하고 나머지 모듈로 4를 취하십시오

(+|:)역전 ( |-우리는 :그것을 모나 딕으로 강제 해야합니다 )과 옮김 ( +- "기차"에서 가장 오른쪽 동사가 아니기 때문에 회전하지 않는 함수입니다 .: )

4(+|:)\x 에 4 번 적용 x중간 결과를 유지하면서

,/' 각각 평평하게하다

+ 바꾸어 놓다

( )@' 왼쪽의 각 값을 오른쪽의 각 값으로 색인화

s# 모양을 바꾸다 s


2
코드 설명을 참조하게되어 기쁩니다
Galen Ivanov

1
@GalenIvanov는 물론이다. 나는 이것을 더 이상 골프를 칠 수 없다고 생각하므로 설명을 시도 할 수도 있습니다.
ngn

감사! 귀하의 솔루션으로 k (또는 ngn / k :) 학습을 시작하고 싶습니다
Galen Ivanov

@GalenIvanov J (그리고 APL?)에 대해 잘 알고 있다면 이미 반쯤있다. K는 더 작고 단순하므로 학습을 강력히 추천합니다. 물론 오차드에서 언제든지 이야기를 나누게되어 기쁩니다 . ngn / k는 실제의 일부일 뿐이지 만 빠르고 실용적으로 만드는 것을 목표로합니다.
ngn

예, 시도해 볼 것 같습니다.
Galen Ivanov

3

JavaScript (ES6), 99 바이트

f=(a,k=m=~-a.length/2)=>~k?f(a.map((r,y)=>r.map(v=>y-m>k|m-y>k|--x*x>k*k?v:a[m+x][y],x=m+1)),k-1):a

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

방법?

W

m=W12tx,y=max(|ym|,|xm|)

tx,yW=5m=2

(2222221112210122111222222)

k=m(x,y)

tx,yk

다른 것들은 바뀌지 않은 채로 있습니다.

이것은 다음과 같은 경우 셀이 회전 하지 않는다는 것과 같습니다 .

(와이>케이) 또는 (와이>케이) 또는 (엑스2>케이2) 와 엑스=엑스

이것은 코드에서 사용되는 테스트입니다.

a.map((r, y) =>
  r.map(v =>
    y - m > k | m - y > k | --x * x > k * k ?
      v
    :
      a[m + x][y],
    x = m + 1
  )
)

케이케이=1케이=/2

~k === 0

3

젤리 , 24 바이트

ṙ⁹ṙ€
ḊṖ$⁺€ßḷ""ç1$ç-ZUµḊ¡

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

나는 이것이 훨씬 짧을 수 있다고 생각합니다.


나는 이와 같은 해결책에 대해 궁금했다! 그건 ḷ""나에게 마법의 외모에 대한 설명을 추가하는 신경 ^^?
Lynn

@Lynn 내가 기대했던 것은 ḷ""마술 이라고 들었습니다 . 그것은 단지 ḷ"여분의 것입니다 "... 오, ḷ"종종 "발명 된"것으로 종종 사용되지 않는 약간의 가능성 이 있습니다. 입력도 포함 할 수 있습니다 0).
Outgolfer Erik

2

하스켈 , 108 바이트

e=[]:e
r=foldl(flip$zipWith(:))e
g!(h:t)=h:g(init t)++[last t]
f[x,y]=r[x,y]
f[x]=[x]
f x=r$(r.r.r.(f!).r)!x

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

Laikoni의 조옮김을 사용 하여 배열을 90도 회전하기 위해 조금 수정했습니다.

  e=[]:e;foldr(zipWith(:))e.reverse
 e=[]:e;foldl(flip$zipWith(:))e

설명

r 배열을 90 ° 회전합니다.

(!)“중앙에 적용”의 상위 기능입니다. g![1,2,3,4,5]입니다 [1] ++ g[2,3,4] ++ [5].

f 토네이도 함수입니다. 기본 사례의 크기는 1과 2입니다 (어떻게 든 0이 작동하지 않음).

마지막 줄은 마술이 일어나는 곳입니다. 우리 r.r.r.(f!).r는 중간 줄에 적용한 x다음 결과를 회전시킵니다. 중간 행 M 이라고하겠습니다 . 우리는 중간에 재귀 할 컬럼M , 그리고 그에서 얻을, 우리가 회전 할 수 M 후 사용 (f!). 그런 다음 M을 원래 방향으로 다시 r.r.r회전시키는 데 사용 합니다.


2

Java 10, 198192 바이트

m->{int d=m.length,b=0,i,j;var r=new Object[d][d];for(;b<=d/2;b++){for(i=b;i<d-b;i++)for(j=b;j<d-b;)r[j][d+~i]=m[i][j++];for(m=new Object[d][d],i=d*d;i-->0;)m[i/d][i%d]=r[i/d][i%d];}return r;}

@ceilingcat 덕분에 -6 바이트 .

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

설명:

m->{                         // Method with Object-matrix as both parameter and return-type
  int d=m.length,            //  Dimensions of the matrix
      b=0,                   //  Boundaries-integer, starting at 0
      i,j;                   //  Index-integers
  var r=new Object[d][d];    //  Result-matrix of size `d` by `d`
  for(;b<=d/2;b++){          //  Loop `b` in the range [0, `d/2`]
    for(i=b;i<d-b;i++)       //   Inner loop `i` in the range [`b`, `d-b`)
      for(j=b;j<d-b;)        //    Inner loop `j` in the range [`b`, `d-b`)
        r[j][d+~i]=          //     Set the result-cell at {`j`, `d-i-1`} to:
          m[i][j++];         //      The cell at {`i`, `j`} of the input-matrix
    for(m=new Object[d][d],  //   Empty the input-matrix
        i=d*d;i-->0;)        //   Inner loop `i` in the range (`d*d`, 0]
      m[i/d][i%d]            //     Copy the cell at {`i/d`, `i%d`} from the result-matrix
        =r[i/d][i%d];}       //      to the replaced input-matrix
  return r;}                 //  Return the result-matrix as result

b기본적으로 우리가 어느 반지에 있는지를 나타내는 데 사용됩니다. 그런 다음 반복 할 때마다 시계 방향으로 한 번만 시계 방향으로이 링을 회전시킵니다.

입력 행렬의 교체는 Java가 참조로 전달되므로 수행되므로 단순히 설정 r=m하면 셀에서 복사 할 때 두 행렬이 모두 수정되어 잘못된 결과가 발생합니다. 그러므로 우리는 새로운 것을 만들어야합니다Object 행렬 (새 참조) 모든 셀의 값을 하나씩 복사해야합니다.


1

MATLAB, 93 바이트

function m=t(m),for i=0:nnz(m),m(1+i:end-i,1+i:end-i)=(rot90(m(1+i:end-i,1+i:end-i),3));end;end

나는 이것이 어떻게 든 골프를 칠 수 있다고 확신합니다.

설명

function m=t(m),                                                                          end % Function definition
                for i=0:nnz(m),                                                       end;    % Loop from 0 to n^2 (too large a number but matlab indexing doesn't care)
                                                            m(1+i:end-i,1+i:end-i)            % Take the whole matrix to start, and then smaller matrices on each iteration
                                                      rot90(                      ,3)         % Rotate 90deg clockwise (anti-clockwise 3 times)
                               m(1+i:end-i,1+i:end-i)=                                        % Replace the old section of the matrix with the rotated one


1

하스켈, 274 바이트

w 유형이있는 주요 기능입니다. [[a]] -> [[a]] 예상 이 있습니다.

보다 숙련 된 Haskell 골퍼가이를 개선 할 수 있다고 확신합니다.

w m|t m==1=m|0<1=let m'=p m in(\a b->[h a]++x(\(o,i)->[h o]++i++[f o])(zip(tail a)b)++[f a])m'(w(g m'))
p m|t m==1=m|0<1=z(:)(f m)(z(\l->(l++).(:[]))(r(x h(i m)):(p(g m))++[r(x f(i m))])(h m))
t[]=1
t[[_]]=1
t _=0
h=head
f=last
x=map
i=tail.init
g=x i.i
z=zipWith
r=reverse

Haskell에서의 골프 팁을 확인하고 싶을 수도 있습니다. 예를 들어 조건 대신 가드를 사용 하면 약간의 바이트가 절약됩니다.
Laikoni
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.