文章目录
- 公式
- RGB转HSI
- HSI转RGB
- RGB转HSI代码
- HSI转RGB代码
- 示例
公式
HSI彩色模型就是色调(hub)、饱和度(saturation)、亮度(intensity)
- 色调:描述纯色(纯黄色、纯蓝色之类)的颜色属性
- 饱和度:描述一种纯色被白光稀释的程度
- 亮度:即强度(类似灰度级的感觉)
以下公式来源论文《Color image enhancement with exact HSI color model》
RGB转HSI
I = R + G + B 3 I=\frac{R+G+B}{3} I=3R+G+B
H = { θ , if B ≤ G 36 0 ∘ − θ , if B > G 其 中 θ = cos − 1 { 1 2 [ ( R − G ) + ( R − B ) ] [ ( R − G ) 2 + ( R − B ) ( G − B ) ] 1 / 2 } H=\left\{\begin{array}{ll} \theta, & \text { if } B \leq G \\ 360^{\circ}-\theta, & \text { if } B>G \end{array}\right. \\其中 \theta=\cos ^{-1}\left\{\frac{\frac{1}{2}[(R-G)+(R-B)]}{\left[(R-G)^{2}+(R-B)(G-B)\right]^{1 / 2}}\right\} H={θ,360∘−θ, if B≤G if B>G其中θ=cos−1{[(R−G)2+(R−B)(G−B)]1/221[(R−G)+(R−B)]}
S = 1 − 3 min ( R , G , B ) R + G + B S=1-\frac{3\min (R, G, B)}{R+G+B} S=1−R+G+B3min(R,G,B)
HSI转RGB
- 0 ∘ ≤ H < 12 0 ∘ 0^{\circ} \leq H<120^{\circ} 0∘≤H<120∘
B = I ( 1 − S ) R = I [ 1 + S cos H cos ( 6 0 ∘ − H ) ] G = 3 I − ( R + B ) \begin{aligned} B &=I(1-S) \\ R &=I\left[1+\frac{S \cos H}{\cos \left(60^{\circ}-H\right)}\right] \\ G &=3 I-(R+B) \end{aligned} BRG=I(1−S)=I[1+cos(60∘−H)ScosH]=3I−(R+B) - 12 0 ∘ ≤ H < 24 0 ∘ 120^{\circ} \leq H<240^{\circ} 120∘≤H<240∘
H = H − 24 0 ∘ R = I ( 1 − S ) G = I [ 1 + S cos H cos ( 6 0 ∘ − H ) ] B = 3 I − ( R + G ) \begin{aligned} H&=H-240^{\circ}\\ R &=I(1-S) \\ G &=I\left[1+\frac{S \cos H}{\cos \left(60^{\circ}-H\right)}\right] \\ B &=3 I-(R+G) \end{aligned} HRGB=H−240∘=I(1−S)=I[1+cos(60∘−H)ScosH]=3I−(R+G) - 24 0 ∘ ≤ H < 36 0 ∘ 240^{\circ} \leq H<360^{\circ} 240∘≤H<360∘
H = H − 24 0 ∘ G = I ( 1 − S ) B = I [ 1 + S cos H cos ( 6 0 ∘ − H ) ] R = 3 I − ( G + B ) \begin{aligned} H &=H-240^{\circ}\\ G & =I(1-S) \\ B &=I\left[1+\frac{S \cos H}{\cos \left(60^{\circ}-H\right)}\right] \\ R &=3 I-(G+B) \end{aligned} HGBR=H−240∘=I(1−S)=I[1+cos(60∘−H)ScosH]=3I−(G+B)
RGB转HSI代码
Mat RGB2HSI(const Mat & rgb){Mat hsi(rgb.rows, rgb.cols, rgb.type());float H=0, S=0, I=0;for(int i=0; i < rgb.rows; i++)for(int j=0; j < rgb.cols; j++){float B = rgb.at<Vec3b>(i, j)[0] / 255.f,G = rgb.at<Vec3b>(i, j)[1] / 255.f,R = rgb.at<Vec3b>(i, j)[2] / 255.f;float num = (R - G + R - B) / 2,den = sqrt((R - G) * (R - G) + (R - B) * (G - B)),theta = acos(num/den);if(den == 0) H = 0; // 分母不能为0else H = B <= G ? theta / (2 * MY_PI) : 1 - theta / (2 * MY_PI);float sum = B + G + R;if(sum == 0) S = 0;else S = 1 - 3 * min(min(B, G), R) / sum;I = sum/3.0;hsi.at<Vec3b>(i, j)[0] = H*255;hsi.at<Vec3b>(i, j)[1] = S*255;hsi.at<Vec3b>(i, j)[2] = I*255;}return hsi;
}
HSI转RGB代码
Mat HSI2RGB(const Mat & hsi){Mat rgb(hsi.rows, hsi.cols, hsi.type());float R=0,G=0,B=0;for(int i=0; i < hsi.rows; i++)for(int j=0; j < hsi.cols; j++){float H = hsi.at<Vec3b>(i, j)[0] / 255.f * 2 * MY_PI,S = hsi.at<Vec3b>(i, j)[1] / 255.f,I = hsi.at<Vec3b>(i, j)[2] / 255.f;if(H < 120.f * MY_PI / 180.f){B=I*(1-S);R=I*(1+ S*cos(H)/cos(60.f* MY_PI / 180.f-H));G=3*I-R-B;}else if(H >= 120.f * MY_PI / 180.f && H < 240 * MY_PI / 180.f){H-=(120.f * MY_PI / 180.f);R=I*(1-S);G=I*(1+ S*cos(H)/cos(60.f* MY_PI / 180.f-H));B=3*I-R-G;}else if(H >= 240.f * MY_PI / 180.f){H-=(240.f * MY_PI / 180.f);G=I*(1-S);B=I*(1+ S*cos(H)/cos(60.f* MY_PI / 180.f-H));R=3*I-B-G;}rgb.at<Vec3b>(i, j)[0] = B*255;rgb.at<Vec3b>(i, j)[1] = G*255;rgb.at<Vec3b>(i, j)[2] = R*255;}return rgb;
}
示例
#include<iostream>
#include <opencv2/opencv.hpp>
#define MY_PI 3.1415
using namespace std;
using namespace cv;
Mat RGB2HSI(const Mat & rgb);
Mat HSI2RGB(const Mat & hsi);
int main(int argc, char * argv[]){Mat img = imread("../image/RGB.jpg");imshow("origin", img);waitKey();Mat hsi = RGB2HSI(img);imshow("hsi", hsi);waitKey();Mat rgb=HSI2RGB(hsi);imshow("rgb", rgb);waitKey();return 0;
}