BGR到HSV转换的意外量化

时间:2016-01-24 17:51:44

标签: c++ opencv opencv3.0 hsv

我正在尝试将BGR图像转换为HSV。当我写出转换的H通道时,它有一个奇怪的块状结构,我猜这意味着在此过程中意外量化了一些东西。我尝试将我的BGR unsigned char图像转换为float,但结果是一样的。这是我的代码:

// STL
#include <iostream>

// OpenCV
#include <opencv2/opencv.hpp>

void Float(const std::string& inputFilename)
{
    cv::Mat image = cv::imread(inputFilename, CV_LOAD_IMAGE_COLOR); // Loads as BGR

    cv::Mat floatImage;
    image.convertTo(floatImage, CV_32FC3);

    cv::Mat hsvImage;
    cv::cvtColor(floatImage, hsvImage, CV_BGR2HSV);

    std::vector<cv::Mat> hsvChannels;
    cv::split(hsvImage, hsvChannels);

    cv::imwrite("h_float.png", hsvChannels[0]);

}

void Original(const std::string& inputFilename)
{
    cv::Mat image = cv::imread(inputFilename, CV_LOAD_IMAGE_COLOR); // Loads as BGR

    cv::Mat hsvImage;
    cv::cvtColor(image, hsvImage, CV_BGR2HSV);

    std::vector<cv::Mat> hsvChannels;
    cv::split(hsvImage, hsvChannels);

    cv::imwrite("h_original.png", hsvChannels[0]);

}

int main(int argc, char* argv[])
{
    std::string inputFilename = argv[1];

    Original(inputFilename);
    Float(inputFilename);

    return EXIT_SUCCESS;
}

这是输入: enter image description here

和输出(h_original.png): enter image description here

和输出(h_float.png): enter image description here

关于我在这里做错了什么建议?

1 个答案:

答案 0 :(得分:0)

你正在以正确的方式做所有事情。我在我的机器上尝试了你的图像并得到了相同的结果。我认为这个结果是由于图像的色彩范围较小。这是HSV 3通道的结果。 H和S遭受这个问题。然而,V是光滑的,因为它是关于光线条件而不是颜色。

H-channel

S-channel

V-channel

修改

为了使我的观点更清晰,请使用相同的代码查看此图像和输出:

Original RGB

H-channel

S-channel

V-channel

另一个编辑(黑色问题):

HSVif V=0 then it is black其余SH。 因此,要检查颜色是否为黑色,您只需检查V组件,如果检查另一个则没有意义。

数学证明:

C = V × S
X = C × (1 - |(H / 60º) mod 2 - 1|)
m = V - C

HSV-RGB

很明显,当V=0H,S时,我们会: C=0 , X=0导致R,G,B=(0,0,0)