2012-09-20 6 views
7

aquí está el problema: cargo una imagen en escala de grises con OpenCV v.2.4.2. Ahora quiero saber, por ejemplo, el valor del píxel en la posición (0,0). He intentado:Los valores de la matriz de Opencv muestran

Mat image=imread("00001.jpg",1); 
cvtColor(image,image,CV_RGB2GRAY); 
int a=image.at<unsigned>(0,1); 
printf("%d ",a); 

En realidad, esto no funciona. ¿Cómo obtener el valor de píxel con cualquier tipo de datos (CV_8U, CV_32S ...)?

Gracias !!!

+0

¿Está utilizando (0,1) en lugar de (0,0)? – count0

Respuesta

4

Estás cometiendo dos errores aquí.

Al leer la imagen, está especificando 1 como argumentos de entrada. Como se explica en imread, la función puede leer imágenes en tres formatos diferentes.

CV_LOAD_IMAGE_UNCHANGED (< 0) carga la imagen como es (incluyendo el canal alfa si está presente) CV_LOAD_IMAGE_GRAYSCALE (0) carga la imagen como una intensidad de uno
CV_LOAD_IMAGE_COLOR (> 0) carga la imagen en el formato RGB

para su caso tendrá que utilizar CV_LOAD_IMAGE_GRAYSCALE como segundo argumento

En el siguiente paso en el que está utilizando: image.at<unsigned>(0,1); que no hace corr espond a cualquier cosa. usted usa <unsigned> pero el compilador dice "¿NO FIRMADO? ¿SIN FIRMAR qué ???"

Creo que una mejor manera de hacerlo es utilizar etiquetas correctas como CV_LOAD_IMAGE_COLOR o CV_LOAD_IMAGE_GRAYSCALE. En el siguiente ejemplo, estoy leyendo la imagen en un canal (CV_LOAD_IMAGE_GRAYSCALE), que lo convierte automáticamente en escala de grises.

#include <cv.h> 
#include <highgui.h> 

#include <iostream> 

using namespace std; 
using namespace cv; 

int main() 
{ 
    Mat gImg = imread("img.png", CV_LOAD_IMAGE_GRAYSCALE); 

    uchar val; 
    val = gImg.at<uchar>(0,0); 

    cout << (int)val << endl; 

    imshow("showImg",gImg); 
    cvWaitKey(0); 

    return 1; 
} 
+0

Bien, vale, esto funciona, pero ¿has probado lo que esto realmente produce? En mi caso, obtengo -89 por píxel (0,0). ¿Cómo es esto posible cuando la imagen tiene 8 bits sin firmar? luego me gustaría preguntar ¿por qué usas uchar? –

+0

por supuesto que lo he intentado. No sé por qué no estás obteniendo la salida correctamente. He usado UCHAR exactamente por la misma razón que se explica en el comentario anterior por @ count0, es decir, puede representar un valor entre 0 y 255 – masad

+1

No puede usar imread de esta manera. El segundo argumento es un indicador que es 0,> 0 o <0 dependiendo de si desea leer la escala de grises de la imagen, el color de 3 canales o como está. No puedes especificar el tipo exactamente. Simplemente se ejecuta en el caso específico porque CV_8U == 0 – Sassa

0

Se podría tratar de averiguar lo que representó OpenCV con tener una mejor idea de qué tipo de empleo:

cout << image.depth() << ", " << image.channels() << endl; 

También puedes ver este discussion sobre el acceso elemento.

+0

Bueno, conozco la profundidad y los canales, pero si sé que la matriz es para la imagen habitual de 8 bits y un entero sin signo para que la matriz sea CV_8UC1, ¿qué parámetro debería pasar a Mat :: at? exactamente a aquí: image.at (0,1); –

+0

CV_8UC1 significa un canal único sin signo de 8 bits, por lo que sería 'char sin signo' que representa valores de 0..255. El entero sin signo representaría valores de 0..65536 que serían CV_16UC1. – count0

0

En primer lugar, no hay una forma genérica de obtener el valor de píxel de esta manera. Lo que significa que siempre debe especificar el tipo correcto de sus valores si va a utilizar at. En este caso, debe hacer a=image.at<uchar>(0,1); ya que convierte su imagen a escala de grises sin signo de 8 bits (1-channel).

También debería usar CV_BGR2GRAY en lugar de RGB2GRAY ya que OpenCV usa BGR como el orden de los canales.

También puede leer su imagen en escala de grises desde el principio y utiliza uchar nuevo:

Mat image = imread("00001.jpg",0); // note the 0 flag 
int a=image.at<uchar>(0,1); 
printf("%d ",a); 
1

hay una manera fácil de hacer esto.

Mat tiene Mat.data da un puntero que hace referencia a la matriz de datos original.

Para obtener los valores de píxeles de la fila n y la columna m-ésima,

Mat img = imread("filename.jpg",CV_LOAD_IMAGE_COLOR); 
unsigned char *input = (unsigned char*)(img.data); 

int i,j,r,g,b; 
for(int i = 0;i < img.cols;i++){ 
    for(int j = 0;j < img.rows;j++){ 
     b = input[img.cols * j + i ] ; 
     g = input[img.cols * j + i + 1]; 
     r = input[img.cols * j + i + 2]; 
    } 
} 

Por lo tanto, se trata de una imagen en color. para las imágenes en escala de grises,

Mat img = imread("filename.jpg",CV_LOAD_IMAGE_COLOR); 
Mat g; 
cvtColor(img, g, CV_BGR2GRAY); 
unsigned char *input = (unsigned char*)(g.data); 

int i,j,r,g,b; 
for(int i = 0;i < img.cols;i++){ 
    for(int j = 0;j < img.rows;j++){ 
     g = input[img.cols * j + i]; 
    } 
} 

Lea más en este blogpost.

Cuestiones relacionadas