LINUX.ORG.RU

Как работает numpy.unique для 2-мерных массивов?

 ,


0

1

Потребовалось посчитать число уникальных цветов в 24-битном PNG. Можно тупо перебирать тройки байт RGB, сравнивать с пополняемым массивом, добавлять в массив, когда появляется что-то новое. Можно воспользоваться средствами Numpy для поиска уникального элемента в массиве: reshape-ом развернуть 3-мерный массив из 1000х1000х3 в 1000000х3, затем unique-ом найти уникальные тройки.

from PIL import Image
import numpy as np
im = Image.open('.....')
ar = np.asarray(im)

arlinear = np.reshape( ar, (ar.shape[0]*ar.shape[1], 3) )
print( len( np.unique( arlinear, axis=0 ) ) )

colourarray = [] 
for line in ar:
    for pixel in line:
        if not np.any(colourarray==pixel):
            colourarray.append(pixel)
print(len(colourarray))

Результат отличается. Почему?

Ответ: unique отработал правильно. Проблема в any(): np.any([[True, False], [False, False]]) будет True. Сравнение циклом находит совпадения, когда совпадает 1 цвет.

★★★★★

Последнее исправление: question4 (всего исправлений: 2)

Ответ на: комментарий от aquadon

Да, print выдаёт массив троек цветов.

И упреждая вопрос, да axis=0 даёт в результате сортированный массив троек цветов. В отличии от axis=1.

question4 ★★★★★
() автор топика
Ответ на: комментарий от question4

Так сделай тест, дай малый массив данных на вход и посмотри, какой из ответов правильный. Потом будет проще разобраться.

aquadon ★★★★★
()
Ответ на: комментарий от aquadon

Так и сделал. Поэтому и спрашиваю. Откуда-то берутся посторонние тройки.

question4 ★★★★★
() автор топика
Ответ на: комментарий от aquadon

Нашёл.

np.any( np.array( ( (1, 2, 3), (4, 5, 6) ) ) == [1,1,1] ) вернёт True, так как будет 1 частичное совпадение: [[True, False, False], [False, False, False]] и этого достаточно.

question4 ★★★★★
() автор топика
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.