У меня есть сочетание трехканальных изображений в градациях серого и цветных изображений в каталоге, и я хотел бы в меру подсчитать, насколько RGB-изображение на самом деле является эмпирически серым, и чтобы его можно было очень эффективно вычислить.
Я понимаю, что если R == G == B, у меня пиксел в градациях серого, а если R, G, B на пиксель не равны, у меня цветной пиксель. Я согласен с тем, чтобы сказать, что оттенки серого - это то, какая доля пикселей по сравнению с цветными оттенками Все истинные изображения в градациях серого должны иметь оценку == 1.
Я сделал глупую метрику, которая работает в PIL:
>>> from PIL import Image
>>> im = Image.open(filename)
>>> sum([1 for pixel in im.getdata() if (pixel[0]==pixel[1]==pixel[2])])/len(list(im.getdata()))
Для произвольного цвета im ==:
0.0003056384175265294
Для градаций серого == 1011 *
1.0
Так что это работает как ожидалось.
Как правильно транслировать это правильно, если предположить, что я начинаю с массива или тензорного потока, а не с файла, к которому я могу получить доступ к необработанным пикселям в PIL?
Я начинаю с:
sess = tf.Session()
dat = tf.read_file(filename)
ten = tf.image.decode_jpeg(dat)
x = sess.run(ten)
>>> x[0,0,:]
array([255, 255, 255], dtype=uint8)
выглядит хорошо. Я попробовал следующее, которое, похоже, не дает того, что я искал:
def grayscaler(x):
"""Input is a pixel. Compare R == G == B"""
if (x[0] == x[1] == x[2]):
return 1
else:
return 0
>>> np.mean(np.apply_along_axis(grayscaler , axis=2, arr=x))
К сожалению, независимо от изображения, цвета или оттенков серого, я всегда получаю 1, цвет или оттенки серого, поэтому моя функция выше не переводится правильно.
>>> np.mean(np.apply_along_axis(grayscaler, axis=2, arr=x))
1.0
Каков правильный синтаксис и функция для зацикливания всех трех цветовых каналов попиксельным образом для массива-пустышки?