Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
213 views
in Technique[技术] by (71.8m points)

c++ - Optimising getting OR of Mat Channels

I want to to convert a BGR cv::Mat to gray using this formula Gray=B OR G OR R; pixel-wise operation. I tried this:

cv::Mat diff_channels[3];
cv::split(diff, diff_channels);
diff = diff_channels[0] | diff_channels[1] | diff_channels[2];

Can this be achieved with better approach?

Also, if I want to achieve Gray=MAX(B,G,R); pixel-wise operation any suggestion ?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

OpenCV doesn't contain any suitable built-in function to process separate channels in such way. If you want to get maximum performance you may implement this procedure by yourself. I suggest you something like this:

void calcOrChannels(const cv::Mat& src, cv::Mat& dst)
{
  CV_Assert(src.type() == CV_8UC3);
  int rows = src.rows, cols = src.cols;

  dst.create(src.size(), CV_8UC1);

  if (src.isContinuous() && dst.isContinuous())
  {
    cols = rows * cols;
    rows = 1;
  }

  for (int row = 0; row < rows; row++)
  {
    const uchar* src_ptr = src.ptr<uchar>(row);
    uchar* dst_ptr = dst.ptr<uchar>(row);

    for (int col = 0; col < cols; col++)
    {
      dst_ptr[col] = src_ptr[0] | src_ptr[1] | src_ptr[2]; // std::max(src_ptr[0], std::max(src_ptr[1], src_ptr[2]))
      src_ptr += 3;
    }
  }
}

Please note that you need to test performance of this function on your hardware, since it loses benefits by using SIMD instruction and parallelism which implemented (or maybe implemeted later) in OpenCV. But this procedure use less additional memory and arithmetical operations. I guess that it would work faster on the most systems (especially embedded). It also depends on sizes of your matrices.

Timings on my system (Core i7-4790):

| Matrix size | OpenCV (ms) | My (ms) |
|:-----------:|------------:|---------|
| 1280*720    | 4           | 1       |
| 1920*1080   | 8           | 2       |
| 4096*3112   | 41          | 17      |

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...