Znajdź sąsiadów komórki

20

... lub Toroidalne dzielnice Moore

Podane liczby całkowite dodatnie h, wi całkowitą nieujemną i, powrót wszystkich indeksów i okolic i.

Przyjmij macierz składającą się z hrzędów welementów, ponumerowanych od najniższego, w lewym górnym rogu, do najwyższego, w prawym dolnym rogu, i zwróć, w dowolnym rozsądnym formacie, listę indeksów, które otaczać indeksu i. Ta macierz jest torusem (nieskończona mapa, która owija się wokół każdej krawędzi).

Na przykład dane wejściowe h=4i w=4, spowodowałyby macierz:

 0  1  2  3 
 4  5  6  7
 8  9 10 11
12 13 14 15

ale dokładniej:

15 12 13 14 15 12
 3  0  1  2  3  0
 7  4  5  6  7  4
11  8  9 10 11  8
15 12 13 14 15 12
 3  0  1  2  3  0

więc jeśli itak 0, musisz wrócić 15, 12, 13, 3, 1, 7, 4, 5(0).

Przykłady

W oparciu o 0:

h   w   i       Expected result

4   4   5       0, 1, 2, 4, 6, 8, 9, 10
4   4   0       15, 12, 13, 3, 1, 7, 4, 5
4   5   1       15, 16, 17, 0, 2, 5, 6, 7
1   3   2       1, 2, 0, 1, 0, 1, 2, 0
1   1   0       0, 0, 0, 0, 0, 0, 0, 0

Na podstawie 1:

h   w   i       Expected result

4   4   6       1, 2, 3, 5, 7, 9, 10, 11
4   4   1       16, 13, 14, 4, 2, 8, 5, 6
4   5   2       16, 17, 18, 1, 3, 6, 7, 8
1   3   3       2, 3, 1, 2, 1, 2, 3, 1
1   1   1       1, 1, 1, 1, 1, 1, 1, 1

Zasady

  • Twoja odpowiedź może być zindeksowana lub 0, twój wybór, proszę podać.
  • Możesz założyć, że i < h * w(lub i <= h * wdla 1-indeksowanych odpowiedzi).
  • Możesz założyć, że i >= 0(lub i > 0dla 1-indeksowanych odpowiedzi).
  • Kolejność zwracanych wartości nie jest ważna, o ile uwzględnione jest tylko osiem pożądanych wartości.
  • Standardowe luki są zabronione .
  • To jest więc wygrywa najkrótsza odpowiedź w każdym języku!

Dzięki @Conor O'Brien za bardziej technicznie brzmiący tytuł i @ngm za więcej przypadków testowych!

Dom Hastings
źródło
3
Czy możemy zwrócić macierz sąsiadów 3 na 3?
Adám
@ Adám Wolę, aby lista nie zawierała komórki środkowej, jeśli to możliwe. Ale doceniam, że są już odpowiedzi. Czy łatwo to odfiltrować?
Dom Hastings,
Czy zamówienie ma znaczenie?
Robert Fraser
@RobertFraser Zamówienie nie jest ważne. Dodam to do zasad.
Dom Hastings,
@DomHastings Interpretuję ten komentarz jako: nie wolno zwracać macierzy 3 na 3 lub uwzględniać komórki środkowej?
JungHwan Min

Odpowiedzi:

8

JavaScript (ES6), 75 bajtów

Zaoszczędzono 2 bajty dzięki @KevinCruijssen

Oczekuje indeksu opartego na 0.

(h,w,i)=>[...'12221000'].map((k,j,a)=>(i+w+~-k)%w+~~(i/w+h+~-a[j+2&7])%h*w)

Wypróbuj online!

Otaczające indeksy są zwracane w następującej kolejności:

543)62)701

W jaki sposób?

Wskaźniki każdej otaczającej komórki w ( x + d x , y + d y ) są podane przez:jarex,rey(x+rex,y+rey)

Idx,dy=((x+dx)modw)+w((y+dy)modh)=((N+dx)modw)+w((Nw+dy)modh)

gdzie to indeks komórki docelowej.N.=wy+x

Przechodzimy przez listę i odejmujemy aby uzyskać wartość , co daje:1 d x[1,2),2),2),1,0,0,0]1rex

[0,1,1,1,0,-1,-1,-1]

Dla odpowiednich wartości używamy tej samej listy przesuniętej o 2 pozycje, co daje:rey

[1,1,0,-1,-1,-1,0,1]
Arnauld
źródło
w*(~~(i/w+h+~-a[j+2&7])%h)aby ~~(a[j+2&7]-1+i/w+h)%h*wzaoszczędzić 2 bajty, pozbywając się z pary nawiasach.
Kevin Cruijssen
@KevinCruijssen Nice catch. Dzięki!
Arnauld,
6

APL (Dyalog Classic) , 27 bajtów

{(⍺⊥⍺|(⍺⊤⍵)-⊢)¨1-14⌽,⍳3 3}

Wypróbuj online!

{ }jest funkcją z argumentami (wymiary h w) i (indeks i)

⍳3 3jest macierzą wszystkich liczb dwucyfrowych trójskładnikowych 2: 0 0, 0 1, ...,2 2

, powiększa macierz jako wektor

1↓4⌽usuwa środkowy element 1 1, obracając 4 w lewo ( 4⌽) i upuszczając jeden ( 1↓)

1- odejmuje od 1, dając wszystkie 8 przesunięć sąsiadów

( stosuje ciąg funkcji w nawiasach do każdego przesunięcia

⍺⊤⍵jest podstawowym kodowaniem współrzędnych w macierzy

(⍺⊤⍵)-⊢ odejmuje bieżące przesunięcie, podając współrzędne sąsiada

⍺|to mod ado zawijania współrzędnych i pozostawania w matrycy

⍺⊥ dekoduje z bazy

ngn
źródło
5

APL (Dyalog Unicode) , 40 bajtów SBCS

Anonimowa funkcja poprawki. Przyjmuje h wjako lewy argument i iprawy argument.

{14⌽,3 3↑,⍨⍣2⍪⍨⍣2⊃⊖∘⍉/(¯1+⍺⊤⍵),⊂⍺⍴⍳×/⍺}

Wypróbuj online!

{} „Dfn”; to lewy argument (wymiary) i prawy argument (indeks).

×/⍺ iloczyn (pomnożenie-pomniejszenie) wymiarów

 pierwszy, że wiele wskaźników

⍺⍴ używać wymiary r eshape tym

 dołącz go (aby traktować jako pojedynczy element)

(), Wstaw następujące:

  ⍺⊤⍵ zakoduj indeks w mieszanej podstawie h w(daje nam to współrzędne indeksu)

  ¯1+ dodaj ujemny do tych współrzędnych

⊖∘⍉/ zmniejsz przez obrócenie-transponowanie
  jest to równoważne z y⊖⍉x⊖⍉…, które jest równoważne z y⊖x⌽…, który obraca w lewo tyle kroków, ile ijest przesunięty w prawo (mniej jeden), i obraca w górę tyle kroków, ile ijest przesunięty w dół (mniej jeden), powodując macierz 3 na 3 staramy się znajdować w lewym górnym rogu

 ujawnij (ponieważ redukcja zredukowała wektor do skalara przez załączenie)

⍪⍨⍣2 stos na sobie dwa razy (tak naprawdę potrzebujemy tylko trzykrotnie dla matryc jednorzędowych)

,⍨⍣2 dołącz do siebie dwa razy (tak naprawdę potrzebujemy tylko trzykrotnie dla matryc jednokolumnowych)

3 3↑ weź pierwsze trzy rzędy pierwszych trzech kolumn

Następne dwa kroki można pominąć, jeśli dopuszczalne jest zwracanie macierzy 3 na 3:

, ravel (spłaszczyć)

4⌽ obróć cztery kroki w lewo (przenosi środkowy element na przód)

1↓ upuść pierwszy element

Adám
źródło
@ Adám napraw powyższe i skróć je: {,(⍺⊥⍺|(⍺⊤⍵)-⊢)¨1-⍳3 3}Nie jestem pewien, czy powinieneś również usunąć środkowy element: {4⌽1↓4⌽...}
ngn 18'18
@ngn Uh, to dość oryginalne. Zamieszczasz to!
Adám
@ Adám ok
ngn
Nie sądzę, że oczekuje się, że wynik będzie zawierał środkowy element.
JungHwan Min.
1
Ostatni przypadek testowy nadal ma 8 elementów. Myślę, że zamierzonym wyjściem jest wydrukowanie sąsiadów w pozycjach względnych[-1, -1], [-1, 0], [-1, 1], [0, -1], [0, 1], [1, -1], [1, 0], [1, 1]
JungHwan Min
4

Python 2 , 79 69 66 bajtów

lambda h,w,i:[(i+q%3-1)%w+(i/w+q/3-1)%h*w for q in range(9)if q-4]

Wypróbuj online!

3 bajty obdarowane przez Neila , który to zauważył (x*w)%(h*w)==((x)%h)*w==(x)%h*w.

Rozwiązanie z indeksowaniem 0.

Chas Brown
źródło
%h*w oszczędza 3 bajty *w%(h*w).
Neil
4

R , 125 111 108 bajtów

function(x,i,m=array(1:prod(x),x),n=rbind(m,m,m),o=cbind(n,n,n),p=which(m==i,T)+x-1)o[p[1]+0:2,p[2]+0:2][-5]

Wypróbuj online!

14 i 8 bajtów gry w golfa przez @JayCe i @Mark.

Dane wejściowe są [w, h], ispowodowane tym, że R wypełnia najpierw kolumnę tablic.

Sprawia, że ​​tablica, a następnie „trzykrotnie” jest pod względem wiersza i kolumny. Następnie zlokalizuj iw oryginalnej tablicy i znajdź jej sąsiedztwo. Wyjście bez i.

ngm
źródło
1
Możesz zapisać 14 bajtów . Nie wiedziałem, co było argumentem arr .ind, nauczyłem się dzisiaj!
JayCe,
Można zapisać 8 bajtów zastępując seq()ze1:
Mark
3

PHP , 165 bajtów

Jest to „oparte na 0”. W PHP musi być lepsze rozwiązanie, ale jest to punkt wyjścia!

<?list(,$h,$w,$i)=$argv;for($r=-2;$r++<1;)for($c=-2;$c++<1;)$r||$c?print(($k=(int)($i/$w)+$r)<0?$h-1:($k>=$h?0:$k))*$w+(($l=$i%$w+$c)<0?$w-1:($l>=$w?0:$l))%$w.' ':0;

Aby uruchomić:

php -n <filename> <h> <w> <i>

Przykład:

php -n cell_neighbours.php 4 5 1

Lub wypróbuj online!

Noc 2
źródło
3

K (ngn / k) , 27 24 bajtów

{x/x!''(x\y)-1-3\(!9)^4}

Wypróbuj online!

{ }jest funkcją z argumentami x(wymiary h w) i y(indeks i)

(!9)^4jest 0 1 2 3 4 5 6 7 8bez4

3\ koduje w trójskładniku: (0 0;0 1;0 2;1 0;1 2;2 0;2 1;2 2)

1-odejmuje od 1, dając przesunięcie sąsiada:(1 1;1 0;1 -1;0 1;0 -1;-1 1;-1 0;-1 -1)

x\yjest podstawowym xkodowaniem ywspółrzędnych yw macierzy

- odejmuje każde przesunięcie, dając nam 8 par współrzędnych sąsiada

x!''jest mod xdla każdego - zawija współrzędne, aby pozostały w matrycy

x/dekoduje z podstawy x- zamienia pary współrzędnych w pojedyncze liczby całkowite

ngn
źródło
Z ciekawości, czy twój wariant K ma przysłówek „odwrotny”, jak J ~?
Conor O'Brien
1
@ ConorO'Brien Żaden z ks, których znam (Kx K, Kona, oK i mój) nie ma go, co jest niefortunne dla golfistów. Jest tylko 6 wbudowanych przysłówków: / \ '/: \:': i nie ma mechanizmu takiego zdefiniowanego przez użytkownika.
ngn
Oczywiście mógłbym dodać przysłówek do selfie, ale gra w golfa nie jest dla ngn / k celem samym w sobie, tylko środkiem do gromadzenia przypadków testowych i doświadczenia.
ngn
To uczciwe. Oczywiście możesz postrzegać to jako potencjalną wadę języka. Użyłem PPCG, aby pomóc w rozwoju Attache, i zdałem sobie sprawę, że Attache nie ma kilku bardzo przydatnych funkcji, których w innym przypadku nie uwzględniałbym. Nie używam K, ale może istnieją inne przypadki użycia, które mogą uzasadniać ten rodzaj przysłówka?
Conor O'Brien
@ ConorO'Brien Znam APL, który jest jak ~w J i jestem przekonany o jego użyteczności, ale widzisz, że k ogranicza się do wydruku ASCII i (prawie) żadnych digrafów, więc nowy przysłówek oznaczałby poświęcenie niektórych innych użytecznych prymitywów, a także większa niezgodność między implementacjami. Nie rozumiem, co mogę, żeby to włożyć.
ngn
2

MATL , 24 bajty

*:2Geti=&fh3Y6&fh2-+!Z{)

Wejścia są h, w, i. Dane wyjściowe to wektor wiersza lub wektor kolumny z liczbami.

Wejścia ii wyjścia są oparte na 1.

Wypróbuj online! Lub sprawdź wszystkie przypadki testowe .

Wyjaśnienie

*     % Take two inputs implicitly. Multiply
      % STACK: 16
:     % Range
      % STACK: [1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16]
2G    % Push second input again
      % STACK: [1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16], 4
e     % Reshape with that number of rows, in column-major order
      % STACK: [1 5 9 13; 2 6 10 14; 3 7 11 15; 4 8 12 16]
t     % Duplicate
      % STACK: [1 5 9 13; 2 6 10 14; 3 7 11 15; 4 8 12 16],
      %        [1 5 9 13; 2 6 10 14; 3 7 11 15; 4 8 12 16]
i=    % Take third input and compare, element-wise
      % STACK: [1 5 9 13; 2 6 10 14; 3 7 11 15; 4 8 12 16],
      %        [0 0 0 0; 0 1 0 0; 0 0 0 0; 0 0 0 0]
&f    % Row and column indices of nonzeros (1-based)
      % STACK: [1 5 9 13; 2 6 10 14; 3 7 11 15; 4 8 12 16], 2, 2,
h     % Concatenate horizontally
      % STACK: [1 5 9 13; 2 6 10 14; 3 7 11 15; 4 8 12 16], [2 2]
3Y6   % Push Moore mask
      % STACK: [1 5 9 13; 2 6 10 14; 3 7 11 15; 4 8 12 16], [2 2],
      %        [1 1 1; 1 0 1; 1 1 1]
&f    % Row and column indices of nonzeros (1-based)
      % STACK: [1 5 9 13; 2 6 10 14; 3 7 11 15; 4 8 12 16], [2 2],
      %        [1; 2; 3; 1; 3; 1; 2; 3], [1; 1; 1; 2; 2; 3; 3; 3] 
h     % Concatenate horizontally
      % STACK: [1 5 9 13; 2 6 10 14; 3 7 11 15; 4 8 12 16], [2 2],
      %        [1 1; 2 1; 3 1; 1 2; 3 2; 1 3; 2 3; 3 3] 
2-    % Subtract 2, element-wise
      % STACK: [1 5 9 13; 2 6 10 14; 3 7 11 15; 4 8 12 16], [2 2],
      %        [-1 -1; 0 -1; 1 -1; -1 0; -1 0; -1 1; 0 1; 1 1] 
+     % Add, element-wise with broadcast
      % STACK: [1 5 9 13; 2 6 10 14; 3 7 11 15; 4 8 12 16],
      %        [1 1; 2 1; 3 1; 1 2; 3 2; 1 3; 2 3; 3 3]
!     % Transpose
      % STACK: [1 5 9 13; 2 6 10 14; 3 7 11 15; 4 8 12 16],
      %        [1 2 3 1 3 1 2 3; 1 1 1 2 2 3 3 3]
Z{    % Convert into a cell array of rows
      % STACK: [1 5 9 13; 2 6 10 14; 3 7 11 15; 4 8 12 16],
      %        {[1 2 3 1 3 1 2 3], [1 1 1 2 2 3 3 3]}
)     % Index. A cell array acts as an element-wise (linear-like) index
      % STACK: [1 2 3 5 7 9 10 11]
Luis Mendo
źródło
2

Wolfram Language (Mathematica) , 74 bajty

Mod[i=#;w=#2;Mod[i+#2,w]+i~Floor~w+w#&@@@{-1,0,1}~Tuples~2~Delete~5,1##2]&

Wypróbuj online!

Pobiera dane wejściowe w odwrotnej kolejności ( i, w, h0).

Matryca 3x3 z umieszczoną w niej komórką środkową (60 bajtów)

(Join@@(p=Partition)[Range[#2#]~p~#,a={1,1};3a,a,2a])[[#3]]&

Takes ( w, h, i), 1-oparty.

Wypróbuj online!

JungHwan Min
źródło
2

Partia, 105 bajtów

@for /l %%c in (0,1,8)do @if %%c neq 4 cmd/cset/a(%3/%2+%1+%%c/3-1)%%%1*%2+(%3%%%2+%2+%%c%%3-1)%%%2&echo.

0-indeksowane. Zaoszczędzono 23 bajty, kradnąc sztuczkę modulo 3 ChasBrown.

Neil
źródło
2

MATL, 24 bajty

X[h3Y6&fh2-+1GX\1Gw!Z}X]

Wypróbuj na MATL Online

Przyjmuje dane wejściowe [w h]i i. 8 bajtów zostało bezwstydnie skradzionych z inspiracji odpowiedzią Luisa Mendosa, choć ogólne podejście jest inne.

sundar - Przywróć Monikę
źródło
1

Czysty , 85 83 bajtów

import StdEnv
r=(rem)
$h w i=tl[r(n+i/w)h*w+r(r(m+i)w)w\\n<-[0,1,h-1],m<-[0,1,w-1]]

Wypróbuj online!

Traktuje ijako współrzędną (0 <= p < h, 0 <= q < w)i generuje wartości sąsiednich elementów, w których wartość jest p'w + q'.

Obrzydliwe
źródło
1

Galaretka , 20 bajtów

PRs©Ṫ{œi+€Ø-Ż¤ŒpḊœị®

Dyadyczny link akceptujący listę wymiarów po lewej stronie, [h,w]a komórka jako liczba całkowita po prawej stronie i, co daje listę sąsiedztwa.

Uwaga: kolejność jest inna niż w przykładach dozwolonych w PO

Wypróbuj online!

W jaki sposób?

PRs©Ṫ{œi+€Ø-Ż¤ŒpḊœị® - Link: [h,w], i
P                    - product -> h*w
 R                   - range -> [1,2,3,...,h*w]
    Ṫ{               - tail of left -> w
  s                  - split into chunks -> [[1,2,3,...w],[w+1,...,2*w],[(h-1)*w+1,...,h*w]]
   ©                 - ...and copy that result to the register
      œi             - multi-dimensional index of (i) in that list of lists, say [r,c]
             ¤       - nilad followed by link(s) as a nilad:
          Ø-         -   literal list -> [-1,1]
            Ż        -   prepend a zero -> [0,-1,1]
        +€           - addition (vectorises) for €ach -> [[r,r-1,r+1],[c,c-1,c+1]]
              Œp     - Cartesian product -> [[r,c],[r,c-1],[r,c+1],[r-1,c],[r-1,c-1],[r-1,c+1],[r+1,c],[r+1,c-1],[r+1,c+1]]
                Ḋ    - dequeue -> [[r,c-1],[r,c+1],[r-1,c],[r-1,c-1],[r-1,c+1],[r+1,c],[r+1,c-1],[r+1,c+1]]
                   ® - recall (the table) from the register
                 œị  - multi-dimensional index into (1-indexed & modular)
Jonathan Allan
źródło
1

Attache , 66 bajtów

{a.=[]Moore[Integers@@__2,{Push[a,_]},cycle->1]Flat[a@_][0:3'5:8]}

Wypróbuj online!

Nadal muszę wdrożyć Mooresi NMoore, ale nadal mam, Moorektóry służy jako funkcja iteracji. Zasadniczo Integers@@__2tworzy tablicę liczb całkowitych kształtu __2(dwa ostatnie argumenty) pierwszych Prod[__2]liczb całkowitych. To daje nam tablicę docelową. Następnie Mooreiteruje funkcję{Push[a,_]} po każdym sąsiedztwie wielkości Moore'a 1(domyślny argument), z opcją przełączania każdego elementu ( cycle->1). To dodaje każdą okolicę do tablicy a. Następnie Flat[a@_]spłaszcza trzeci _członek a, czyli okolicę Moore wokół _(pierwszy argument). [0:3'5:8]uzyskuje wszystkich członków oprócz środka z tej spłaszczonej tablicy.

To rozwiązanie z aktualizacją języka wyglądałoby mniej więcej tak (49 bajtów):

{Flat[NMoore[Integers@@__2,_,cycle->1]][0:3'5:8]}
Conor O'Brien
źródło
1

Kotlin , 88 bajtów

Wykorzystuje indeksy oparte na zerach i generuje listę 8 elementów.

{h:Int,w:Int,i:Int->List(9){(w+i+it%3-1)%w+(h+i/w+it/3-1)%h*w}.filterIndexed{i,v->i!=4}}

Wypróbuj online!

JohnWells
źródło