OpenCV Mat array access, which way is the fastest for and why?

后端 未结 4 669
慢半拍i
慢半拍i 2021-01-13 05:39

I am wondering about the way of accessing data in Mat in OpenCV. As you know, we can access to get data in many ways. I want to store image (Width x Height x 1-depth) in Mat

相关标签:
4条回答
  • 2021-01-13 06:29

    You can find information here in the documentation: the basic image container and how to scan images.

    I advice you to practice with at (here) if you are not experienced with OpenCV or with C language types hell. But the fastest way is ptr as Nolwenn answer because you avoid the type checking.

    0 讨论(0)
  • 2021-01-13 06:29

    at<T> does a range check at every call, thus making it slower than ptr<T>, but safer.

    So, if you're confident that your range calculations are correct and you want the best possible speed, use ptr<T>.

    0 讨论(0)
  • 2021-01-13 06:30

    According to the official documentations, they suggest that the most efficient way is to get the pointer to the row first, and then just use the plain C operator []. It also saves a multiplication for each iteration.

    // compute sum of positive matrix elements
    // (assuming that M isa double-precision matrix)
    double sum=0;
    for(int i = 0; i < M.rows; i++)
    {
        const double* Mi = M.ptr<double>(i);
        for(int j = 0; j < M.cols; j++)
            sum += std::max(Mi[j], 0.);
    }
    
    0 讨论(0)
  • 2021-01-13 06:32

    I realize this is an old question, but I think the current answers are somehow misleading.

    Calling both at<T>(...) and ptr<T>(...) will check the boundaries in the debug mode. If the _DEBUG macro is not defined, they will basically calculate y * width + x and give you either the pointer to the data or the data itself. So using at<T>(...) in release mode is equivalent to calculating the pointer yourself, but safer because calculating the pointer is not just y * width + x if the matrix is just a sub-view of another matrix. In debug mode, you get the safety checks.

    I think the best way is to process the image row-by-row, getting the row pointer using ptr<T>(y) and then using p[x]. This has the benefit that you don't have to count with various data layouts and still plain pointer for the inner loop.

    You can use plain pointers all the way, which would be most efficient because you avoid one the multiplication per row, but then you need to use step1(i) to advance the pointer. I think that using ptr<T>(y) is a nice trade-off.

    0 讨论(0)
提交回复
热议问题