jak5z jak5z - 1 month ago 20
C++ Question

OpenCv Mat to array acces

I have problem with acces to data from Mat.data. I perform operations on picture and I need acces to every pixel separatly.
I have to necessairly operate on simple types (float, int etc).
The way I am accesing data is like below:

for (int idx = 0; idx < image.rows; idx++) {
for (int idy = 0; idy < image.cols; idy++) {
int color_tid = idx * image.cols * image.channels() + idy * image.channels();
uint8_t blue = image.data[color_tid];
uint8_t green = image.data[color_tid + 1];
uint8_t red = image.data[color_tid + 2];
float pixelVal = (int) blue + (int) green + (int) red;
(...)
}
}


This approach is working correctly only to square images (NxN pixels), but for NxM there are anomalies outside the square area (smaller edge).
Do anyone know any other way to acces data of the picture Mat?
Example image (correct result):

enter image description here

anomalies (my problem)

enter image description here

Answer

I recommend to follow the data layout in a Mat

enter image description here

so your loop becomes:

for (int r = 0; r < img.rows; ++r)
{
    for (int c = 0; c < img.cols; ++c)
    {
        uchar* ptr  = img.data + img.step[0] * r + img.step[1] * c;
        uchar blue  = ptr[0];
        uchar green = ptr[1];
        uchar red   = ptr[2];

        float pixelVal = blue + green + red;
    }
}

You can eventually perform a little less operations like:

for (int r = 0; r < img.rows; ++r)
{
    uchar* pt = img.data + img.step[0] * r;
    for (int c = 0; c < img.cols; ++c)
    {
        uchar* ptr  = pt + img.step[1] * c;
        uchar blue  = ptr[0];
        uchar green = ptr[1];
        uchar red   = ptr[2];

        float pixelVal = blue + green + red;
    }
}
Comments