Opencv – Modo de escala de grises Vs conversión de color gris

Estoy trabajando en opencv (2.4.11) python (2.7) y estaba jugando con imágenes grises. Encontré un comportamiento inusual al cargar una imagen en modo de escala de grises y al convertir una imagen de BGR a GRIS. El siguiente es mi código experimental:

import cv2 path = 'some/path/to/color/image.jpg' # Load color image (BGR) and convert to gray img = cv2.imread(path) img_gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) # Load in grayscale mode img_gray_mode = cv2.imread(path, 0) # diff = img_gray_mode - img_gray diff = cv2.bitwise_xor(img_gray,img_gray_mode) cv2.imshow('diff', diff) cv2.waitKey() 

Cuando vi la imagen de la diferencia, puedo ver los píxeles de salida en lugar de la imagen de negro azabache. ¿Puedes sugerir alguna razón? ¿Cuál es la forma correcta de trabajar con imágenes grises.

PD: Cuando uso ambas imágenes en SIFT, los puntos clave son diferentes, lo que puede llevar a resultados diferentes, especialmente cuando se trabaja con imágenes de mala calidad.

Nota: Esto no es un duplicado , porque el OP es consciente de que la imagen de cv2.imread está en formato BGR (a diferencia de la pregunta duplicada sugerida que asumió que era RGB, por lo tanto, las respuestas proporcionadas solo resuelven ese problema)

Para ilustrar, he abierto esta misma imagen JPEG en color:

introduzca la descripción de la imagen aquí

una vez usando la conversión

 img = cv2.imread(path) img_gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) 

y otro cargándolo en modo de escala de grises.

 img_gray_mode = cv2.imread(path, cv2.IMREAD_GRAYSCALE) 

Como ha documentado, la diferencia entre las dos imágenes no es perfectamente 0, puedo ver los píxeles de diferencia hacia la izquierda y la parte inferior

introduzca la descripción de la imagen aquí

He resumido la diferencia también para ver

 import numpy as np np.sum(diff) # I got 6143, on a 494 x 750 image 

cv2.imread() todos los modos cv2.imread()

Entre todos los modos IMREAD_ para cv2.imread() , solo IMREAD_COLOR y IMREAD_ANYCOLOR se pueden convertir usando COLOR_BGR2GRAY , y ambos me dieron la misma diferencia con la imagen abierta en IMREAD_GRAYSCALE

La diferencia no parece tan grande. Mi conjetura es que proviene de las diferencias en los cálculos numéricos en los dos métodos (carga de escala de grises frente a conversión a escala de grises)

Naturalmente, lo que usted quiere evitar es ajustar su código en una versión particular de la imagen solo para descubrir que era subóptimo para imágenes provenientes de una fuente diferente.

En resumen, no mezclemos las versiones y los tipos en el proceso de procesamiento.

Así que mantendría las fonts de imagen homogéneas, por ejemplo, si tiene la captura de la imagen de una cámara de video en BGR, entonces usaría BGR como la fuente y haría la conversión de BGR a escala de grises cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)

Viceversa, si mi fuente final es la escala de grises, abriría los archivos y la captura de video en escala de grises cv2.imread(path, cv2.IMREAD_GRAYSCALE)