Найти соседей клетки


20

... или Тороидальные окрестности Мура

Учитывая положительные целые числа h, wи неотрицательное целое число i, возвращать все индексы окружающих i.

Вы должны принять матрицу, состоящую из hстрок wэлементов, пронумерованных от самого низкого в верхнем левом углу до самого высокого в нижнем правом углу, и вернуть, в любом разумном формате, список индексов, которые будут окружить указатель i. Эта матрица является тором (бесконечная карта, которая оборачивается вокруг каждого ребра).

Например, входы h=4и w=4, приведут к матрице:

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

но более конкретно:

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

так что если бы iбыло 0, вам нужно было бы вернуться 15, 12, 13, 3, 1, 7, 4, 5(на основе 0).

Примеры

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

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

правила

  • Ваш ответ может быть 0 или 1 проиндексирован, ваш выбор, пожалуйста, уточните.
  • Вы можете предположить, что i < h * w(или i <= h * wдля 1-индексированных ответов).
  • Вы можете предположить, что i >= 0(или i > 0для 1-индексированных ответов).
  • Порядок возвращаемых значений не важен, если включены только восемь желаемых значений.
  • Стандартные лазейки запрещены .
  • Это поэтому выигрывает самый короткий ответ на каждом языке!

Спасибо @Conor O'Brien за более технически звучащий заголовок и @ngm за дополнительные тестовые примеры!


3
Можем ли мы вернуть матрицу 3 на 3 соседей?
Адам

@ Adám Я бы предпочел, чтобы в списке не было центральной ячейки, если это возможно. Но оцените уже есть ответы. Это достаточно легко отфильтровать?
Дом Гастингс

Имеет ли значение заказ?
Роберт Фрейзер

Порядок @RobertFraser не важен. Я добавлю это к правилам.
Дом Гастингс

@DomHastings Я интерпретирую этот комментарий как: не разрешается возвращать матрицу 3 на 3 или включать центральную ячейку?
JungHwan Мин

Ответы:


8

JavaScript (ES6), 75 байт

Сохранено 2 байта благодаря @KevinCruijssen

Ожидает индекс на основе 0.

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

Попробуйте онлайн!

Окружающие индексы возвращаются в следующем порядке:

54362701

Как?

Индексы каждой окружающей ячейки в точке ( x + d x , y + d y ) определяются как:Idx,dY(x+dИкс,Y+dY)

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

где - индекс целевой клетки.N=wy+x

Мы список и вычитаем чтобы получить значение , которое дает:1 d x[1,2,2,2,1,0,0,0]1dИкс

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

Для соответствующих значений мы используем тот же список, смещенный на 2 позиции, что дает:dy

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

w*(~~(i/w+h+~-a[j+2&7])%h)чтобы ~~(a[j+2&7]-1+i/w+h)%h*wсэкономить 2 байта, избавившись от пары скобок.
Кевин Круйссен

@KevinCruijssen Хороший улов. Благодарность!
Арно

6

APL (Dyalog Classic) , 27 байтов

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

Попробуйте онлайн!

{ }это функция с аргументами (размеры h w) и (индекс i)

⍳3 3матрица из всех 2-значных тройных чисел: 0 0, 0 1, ...,2 2

, зачисляет матрицу в качестве вектора

1↓4⌽удаляет центральный элемент 1 1, поворачивая 4 влево ( 4⌽) и опуская один ( 1↓)

1- вычитает из 1, давая все 8 соседних смещений

( применяет последовательность функций в скобках к каждому смещению

⍺⊤⍵это базовая кодировка - координаты в матрице

(⍺⊤⍵)-⊢ вычитает текущее смещение, давая координаты соседа

⍺|мод, aчтобы обернуть вокруг координат и остаться в матрице

⍺⊥ декодирует с базы


5

APL (Dyalog Unicode) , 40 байтов SBCS

Анонимная инфиксная функция. Принимает h wкак левый аргумент и iкак правый аргумент.

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

Попробуйте онлайн!

{} "Дфн"; левый аргумент (размеры) и правый аргумент (индекс).

×/⍺ произведение (умножение-уменьшение) размеров

 первое что много показателей

⍺⍴ использовать размеры , чтобы г eshape этой

 заключить его (рассматривать как единый элемент)

(), Добавьте следующее:

  ⍺⊤⍵ закодировать индекс в mixed-radix h w(это дает нам координаты индекса)

  ¯1+ добавить отрицательный к этим координатам

⊖∘⍉/ уменьшить на rotate-the-transpose
  это эквивалентно y⊖⍉x⊖⍉... что эквивалентно y⊖x⌽... который вращается влево на столько шагов, сколько iсмещено вправо (меньше единицы), и вращается на столько шагов, сколько iсмещено вниз (меньше единицы), что приводит к матрица 3 на 3 мы стремимся быть в верхнем левом углу

 раскрыть (потому что сокращение привело к скалярному вектору путем включения)

⍪⍨⍣2 сложить поверх себя дважды (нам действительно нужно трижды для однорядных матриц)

,⍨⍣2 добавить к себе дважды (нам действительно нужно трижды для матриц с одним столбцом)

3 3↑ возьмите первые три строки первых трех столбцов

Следующие два шага могут быть опущены, если приемлем возврат матрицы 3 на 3:

, Равель (сплющить)

4⌽ поверните на четыре шага влево (переводит центральный элемент вперед)

1↓ отбросить первый элемент


@ Adám исправьте вышесказанное и сократите его: {,(⍺⊥⍺|(⍺⊤⍵)-⊢)¨1-⍳3 3}я не уверен, стоит ли вам также удалять средний элемент: {4⌽1↓4⌽...}
ngn

@ngn Это довольно оригинально. Вы отправляете это!
Адам

@ Adám в порядке
18:18

Я не думаю, что на выходе ожидается центральный элемент.
ЮнгХван Мин

1
Последний контрольный пример все еще имеет 8 элементов. Я думаю, что предполагаемый результат - напечатать соседей в относительных позициях[-1, -1], [-1, 0], [-1, 1], [0, -1], [0, 1], [1, -1], [1, 0], [1, 1]
JungHwan Мин


4

R , 125 111 108 байт

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]

Попробуйте онлайн!

14 и 8 байтов, сыгранные @JayCe и @Mark.

Входные данные [w, h], iпотому, что сначала R заполняет столбец массивов.

Создает массив, а затем «утраивает» его по строкам и столбцам. Затем найдите iв исходном массиве и найдите его окрестности. Выход без i.


1
Вы можете сохранить 14 байтов . Я не знал того, у кого был аргумент arr.ind, сегодня кое-что узнал!
JayCe

Вы можете сохранить 8 байтов , заменив seq()на1:
Mark

3

PHP , 165 байт

Это "0 на основе". В PHP должно быть лучшее решение, но это отправная точка!

<?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;

Чтобы запустить это:

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

Пример:

php -n cell_neighbours.php 4 5 1

Или попробуйте онлайн!


3

K (нгн / к) , 27 24 байта

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

Попробуйте онлайн!

{ }это функция с аргументами x(размеры h w) и y(индекс i)

(!9)^4это 0 1 2 3 4 5 6 7 8без4

3\ кодирует в троичной форме: (0 0;0 1;0 2;1 0;1 2;2 0;2 1;2 2)

1-вычитает из 1, давая соседние смещения:(1 1;1 0;1 -1;0 1;0 -1;-1 1;-1 0;-1 -1)

x\yэто базовая xкодировка y- координаты yв матрице

- вычитает каждое смещение, давая нам 8 пар соседних координат

x!''мод xдля каждого - обернуть координаты, чтобы остаться в матрице

x/декодирует из базы x- превращает пары координат в одно целое число


Из любопытства, есть ли у вашего варианта K наречие «обратные аргументы», как у J ~?
Конор О'Брайен

1
@ ConorO'Brien Ни у кого из знакомых мне Ks (Kx's K, Kona, OK, и у меня) его нет, что является неудачным для игры в гольф. Есть только 6 встроенных наречий: / \ '/: \:': и нет механизма для таких пользовательских.
нгн

Конечно, я мог бы добавить наречие селфи, но игра в гольф не является самоцелью для ngn / k, а только средством накопления тестовых случаев и опыта.
нгн

Это честно. Конечно, вы можете рассматривать это как потенциальный недостаток языка. Я использовал PPCG для разработки Attache и понял, что в Attache отсутствуют некоторые очень полезные функции, которые я бы не включил. Я не использую K, но, возможно, есть другие варианты использования, которые могут оправдать этот тип наречий?
Конор О'Брайен

@ ConorO'Brien Я знаком с APL, который похож ~на J, и я убежден в его полезности, но, как вы видите, k ограничен печатным ASCII и (почти) никакими орграфами, поэтому новое наречие будет означать жертва некоторого другого полезного примитива так же как больше несовместимости среди реализаций. Я не вижу, что я могу сделать, чтобы вставить это.
NGN

2

MATL , 24 байта

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

Входы h, w, i. Выходными данными является вектор строки или вектор столбца с числами.

Вход iи выход основаны на 1.

Попробуйте онлайн! Или проверьте все тестовые случаи .

объяснение

*     % 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]

2

Wolfram Language (Mathematica) , 74 байта

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

Попробуйте онлайн!

Принимает ввод в обратном порядке ( i, w, h), на основе 0.

Матрица 3x3 с центральной ячейкой (60 байт)

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

Берет ( w, h, i), 1 на основе.

Попробуйте онлайн!


2

Пакетная, 105 байт

@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 индексированные. Сохранено 23 байта путем кражи уловки @ ChasBrown по модулю 3.



1

Чистый , 85 83 байта

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]]

Попробуйте онлайн!

Обрабатывается iкак координата (0 <= p < h, 0 <= q < w)и генерирует значения соседних элементов, в которых находится значение p'w + q'.


1

Желе , 20 байт

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

Диадическая ссылка, принимающая список измерений слева, [h,w]и ячейка в виде целого числа справа i, что дает список окрестностей.

Примечание: порядок отличается от порядка в примерах, который разрешен в OP

Попробуйте онлайн!

Как?

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)

1

Атташе , 66 байт

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

Попробуйте онлайн!

Мне все еще нужно реализовать Mooresи NMoore, но у меня все еще есть, Mooreкоторый выполняет функцию итерации. По сути, Integers@@__2создает целочисленный массив формы __2(последние два аргумента) первых Prod[__2]целых чисел. Это дает нам целевой массив. Затем Mooreвыполняет итерацию функции {Push[a,_]}по каждой окрестности Мура размера 1(подразумеваемый аргумент) с возможностью циклического выполнения каждого элемента ( cycle->1). Это добавляет каждую окрестность в массив a. Затем Flat[a@_]выравнивается _член a, то есть окрестности Мура, центрированные вокруг _(первый аргумент). [0:3'5:8]получает все члены кроме центра из этого сплющенного массива.

Это решение с обновлением языка будет выглядеть примерно так (49 байт):

{Flat[NMoore[Integers@@__2,_,cycle->1]][0:3'5:8]}

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.