有没有办法使用OpenCV均衡每个样本图像的16位直方图?

tom*_*aja 5 c++ opencv image-processing histogram

我正在使用16位/样本图像。
有没有一种(简单的)方法可以对这些图像进行直方图均衡(转换为8bps是不可行的)?

mic*_*ang 5

equalizeHist OpenCV中仅占用8位数据。

但是OpenCV中的图像标准化不限于8位数据。在这里查看其描述。在您的情况下,对函数的调用应类似于:

normalize(src_image, dst_image, 0, 65535, NORM_MINMAX);
Run Code Online (Sandbox Code Playgroud)

如果您要改善图像的对比度,请首先尝试规格化,并且只有在此方法不起作用时,才尝试平衡。规范化更快,破坏性更小。

请参阅:http : //answers.opencv.org/question/3176/improve-contrast-of-a-16u-image/


Sya*_*hya 5

截至目前,OpenCV equalizeHist 仅支持 8 位图像。我已经创建了16位直方图均衡功能,在这里基于OpenCV的执行在这里

void equalizeHist16Bit(const cv::Mat &_src, cv::Mat &_dst)
{
    _dst = _src.clone();

    const int hist_sz = 65536;
    int *hist = new int[hist_sz] {};
    int *lut = new int[hist_sz] {};

    for (int y = 0; y < _src.rows; y++)
        for (int x = 0; x < _src.cols; x++)
            hist[(int)_src.at<unsigned short int>(y, x)]++;

    auto i = 0;
    while (!hist[i]) ++i;

    auto total = (int)_src.total();
    if (hist[i] == total) 
    {
        _dst.setTo(i);
        return;
    }

    float scale = (hist_sz - 1.f) / (total - hist[i]);
    auto sum = 0;

    for (lut[i++] = 0; i < hist_sz; ++i) 
    {
        sum += hist[i];
        lut[i] = cv::saturate_cast<ushort>(sum * scale);
    }

    for (int y = 0; y < _src.rows; y++)
        for (int x = 0; x < _src.cols; x++)
        {
            _dst.at<unsigned short int>(y, x) = lut[(int)_src.at<unsigned short int>(y, x)];
        }
}
Run Code Online (Sandbox Code Playgroud)