Расстояние шахматной доски в матрице изображения

Учитывая матрицу изображения, как я могу получить расположение пикселей, расстояние до шахматной доски которых от пикселя А меньше, чем Д. Мне нужно выполнить это для всех пикселей.

Используя функцию MATLAB bwdist я не смог добиться желаемого результата. Какое решение?

[D,idx] = bwdist(Img,'chessboard');
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
2
0
748
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Ответ принят как подходящий

Учитывая изображение, пиксель и максимальное расстояние:

% Test image
Image = zeros(20,30);

% Maximum chessboard distance from image
maxDist = 7;

% The pixel from which to measure distance
pix = [4,19];

Чтобы найти пиксели, которые находятся на расстоянии шахматной доски от pix меньше, чем maxDist и в границах изображения:

Опция 1: Использование bwdist

% Create a binary image with all pixels zero except 'pix'
bw = zeros(size(Image));
bw(pix(1), pix(2)) = 1;

% Get the chessboard distance transform
[D,idx] = bwdist(bw,'chessboard');

% Get the linear index of 'pix' 
pixInd = sub2ind(size(bw), pix(1), pix(2));

% Find linear indices of pixels who's chessboard distance from pixel are 
% less than 'maxDist'
pointsInd = find(idx == pixInd & D < maxDist);

% Remove 'pix'
pointsInd(pointsInd == pixInd) = [];

% Get the pairs of (x,y) of the pixels
[pointsX, pointsY] = ind2sub(size(bw), pointsInd);

Вариант 2: Использование meshgrid

% Get the range of x and y indices who's chessboard distance from pixel are 
% less than 'maxDist' and in the image bounds
xRange = max((pix(1)-(maxDist-1)),1):min((pix(1)+(maxDist-1)),size(Image,1));
yRange = max((pix(2)-(maxDist-1)),1):min((pix(2)+(maxDist-1)),size(Image,2));

% Create a mesgrid to get the pairs of (x,y) of the pixels
[pointsX, pointsY] = meshgrid(xRange, yRange);
pointsX = pointsX(:);
pointsY = pointsY(:);

% Remove 'pix'
pixIndToRemove = (pointsX == pix(1) & pointsY == pix(2));
pointsX(pixIndToRemove) = [];
pointsY(pixIndToRemove) = [];

Отображение результата:

% Get linear indices of pixels
pointsInd = sub2ind(size(Image), pointsX, pointsY);

% To display the result, create a binary image with all found pixels 
% colored white
bwPoints = zeros(size(Image));
bwPoints(pointsInd) = 1;

% Show points
imshow(bwPoints, 'InitialMagnification', 2000)

% Show pixel grid lines
hold on
[rows, cols] = size(bwPoints);
for row = 0.5 : 1 : (rows + 0.5)
    line([0.5, cols+0.5], [row, row], 'Color', 'r', 'LineWidth', 0.5);
end
for col = 0.5 : 1 : (cols + 0.5)
    line([col, col], [0.5, rows+0.5], 'Color', 'r', 'LineWidth', 0.5);
end

Эффективность и работа в цикле по всем пикселям изображения:

Вариант 2 намного быстрее, чем Опция 1. Сначала я написал Опция 1, потому что в вопросе упоминалось bwdist. Запуск Вариант 2 в цикле можно улучшить, если сначала вычислить пиксели, а затем сместить их в положение каждого пикселя:

% Get the range of x and y indices who's chessboard distance from pixel 
% (0,0) are less than 'maxDist'
xRange = (-(maxDist-1)):(maxDist-1);
yRange = (-(maxDist-1)):(maxDist-1);

% Create a mesgrid to get the pairs of (x,y) of the pixels
[pointsX, pointsY] = meshgrid(xRange, yRange);
pointsX = pointsX(:);
pointsY = pointsY(:);

% Remove pixel (0,0)
pixIndToRemove = (pointsX == 0 & pointsY == 0);
pointsX(pixIndToRemove) = [];
pointsY(pixIndToRemove) = [];

for x=1:size(Image, 1)
    for y=1:size(Image, 2)
        % Get a shifted copy of 'pointsX' and 'pointsY' that is centered
        % around (x, y)
        pointsX1 = pointsX + x;
        pointsY1 = pointsY + y;

        % Remove the the pixels that are out of the image bounds        
        inBounds =...
            pointsX1 >= 1 & pointsX1 <= size(Image, 1) &...
            pointsY1 >= 1 & pointsY1 <= size(Image, 2);

        pointsX1 = pointsX1(inBounds);
        pointsY1 = pointsY1(inBounds);

        % Do stuff with 'pointsX1' and 'pointsY1'
        % ...

    end
end

Спасибо за рабочее решение. Вроде все нормально, но есть тривиальная проблема: местоположение целевого пикселя (pix) включается в пары [pointsX, pointsY], чего быть не должно.

dtr43 28.05.2019 09:53

@dtr43: я отредактировал ответ и удалил целевой пиксель.

Eliahu Aaron 28.05.2019 10:46

Это работает, но в примерном случае (для изображения 434 * 700 пикселей) для вычисления расстояний до шахматной доски для всех пикселей вариант 1 (предлагаемое вами решение) был использован в двух циклах for. Кроме того, есть еще один внутренний цикл, который вычисляет евклидово расстояние между целевым пикселем и окружающими пикселями в пределах расстояния шахматной доски. Этот процесс очень трудоемкий и неэффективный. Есть ли какой-нибудь трюк, чтобы сделать это более эффективным?

dtr43 28.05.2019 21:14

@ dtr43: Вариант 2 намного быстрее. Я отредактировал ответ и добавил раздел о: Эффективность и работа в цикле по всем пикселям изображения

Eliahu Aaron 29.05.2019 12:51

"The aim is to access the location of the pixels whose chessboard distances from pixel A is less than D. The process should be performed for all pixels..."

Поскольку Д создает квадратную область выбора, просто используйте простую математику.

Например: если Д равно 3, то из позиции [x,y] пикселя A...

//# we minus D by 1 since you want less than D (not equal / higher)

Start-X = pixelA.x - (D-1); //from the left
End-X = pixelA.y + (D-1); //to the right

Start-Y = pixelA.y - (D-1); //from the top
End-Y = pixelA.y + (D-1); //to the bottom

Это даст вам квадратный периметр, который представляет требуемую область выбора.

Посмотрите на этот пример изображения ниже:
Каждый квадрат — это пиксель. Если значок «корона» представляет собой пиксель А, а Д равен 3 (где ваш "меньше Д" означает, что Д имеет максимальную длину 2 пикселя), вы видите, как применяется приведенный выше псевдокод?

Спасибо за предложение; Я боюсь, если он может вычислить диагональные окрестности.

dtr43 28.05.2019 09:59

Если я правильно понял ваш комментарий... (1) Шаг ​​на один пиксель влево/вправо, а также шаг на один пиксель вверх/вниз для перемещения по диагонали. (2) Повторяйте шаг (1), пока не будут покрыты все диагональные пиксели.

VC.One 28.05.2019 11:35

Другие вопросы по теме