Удалить пиксели в изображении, которое хранится в виде массива - PullRequest
0 голосов
/ 06 июня 2018

У меня есть простой массив I, в котором хранится N изображений размером P (количество пикселей).Каждое изображение имеет размер P = q*q.

N = 1000 # number of images
q = 10 # length and width of image
P = q*q # pixels of image
I = np.ones((N,P)) # array with N images of size P

Теперь я хочу удалить участки размером ps вокруг выбранного индекса IDX (установить все значения в ноль).

ps = 2 # patch size (ps x ps)
IDX = np.random.randint(0,P,(N,1))

Мой подход состоял в том, чтобы изменить каждое изображение с помощью reshape(q,q) и удалить пиксели вокруг IDX.Здесь у меня проблема в том, что я не знаю, как вычислить позицию внутри изображения, заданного IDX.Кроме того, я должен проверить, находится ли индекс за пределами изображения.

Как решить эту проблему и есть ли способ векторизации этой процедуры?

РЕДАКТИРОВАТЬ:

СС помощью @Brenlla я сделал следующее, чтобы удалить патчи.Проблема с моим подходом состоит в том, что для этого нужны три цикла for, и мне приходится дважды менять каждое изображение.Есть ли способ повысить производительность?Эта часть значительно замедляет мой код.

import numpy as np
import matplotlib.pyplot as plt

def myplot(I):
    imgs = 10
    for i in range(imgs**2):
        plt.subplot(imgs,imgs,(i+1))
        plt.imshow(I[i].reshape(q,q), interpolation="none")
        plt.axis("off")
    plt.show()

N = 10000
q = 28
P = q*q
I = np.random.rand(N,P)

ps = 3
IDX = np.random.randint(0,P,(N,1))

for i in range(N):
    img = I[i].reshape(q,q)
    y0, x0 = np.unravel_index(IDX[i,0],(q,q))
    for x in range(ps):
        for y in range(ps):
            if (x0+x < q) and (y0+y < q):
                img[x0+x,y0+y] = 2.0
    I[i] = img.reshape(1,q*q)

myplot(I)

1 Ответ

0 голосов
/ 07 июня 2018

Да, это может быть сделано, но оно предполагает интенсивное использование np.broadcasting .

Создание данных плюс печатная копия I:

import time

N = 10000
q = 28
P = q*q
ps = 3 
I = np.random.rand(N,P)
IDX = np.random.randint(0,P,(N,1))
I_copy = I.copy()

А теперь запустите решение цикла.Я переключился x0 и y0:

t0=time.clock()
for i in range(N):
    img = I[i].reshape(q,q)
    x0, y0 = np.unravel_index(IDX[i,0],(q,q))
    for x in range(ps):
        for y in range(ps):
            if (x0+x < q) and (y0+y < q):
                img[x0+x,y0+y] = 2.0
    I[i] = img.reshape(1,q*q)
print('With loop: {:.2f} ms'.format(time.clock()*1e3-t0*1e3))

Прибл.276 мс на моей машине.Сейчас вещание:

t0 = time.clock()
x_shift, y_shift = np.meshgrid(range(ps), range(ps))
x, y = np.unravel_index(IDX, (q,q))
#roi for region of interest
roix = x[:,:,None]+x_shift; 
roiy = y[:,:,None]+y_shift;
roix[roix>q-1] = q-1; roiy[roiy>q-1] = q-1;
I_copy.reshape(N,q,q)[np.arange(N)[:, None, None], roix, roiy] = 2.0

print('No loop: {:.2f} ms'.format(time.clock()*1e3-t0*1e3))

print(np.array_equal(I, I_copy))

примерно в 80 раз быстрее

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...