图像RGB到HSV色彩空间转换及其逆变换 - 我坚信阳光灿烂

时间:2024-02-01 08:01:53

图像RGB到HSV色彩空间转换及其逆变换

HSV 即使用 色相(Hue)、饱和度(Saturation)、明度(Value) 来表示色彩的一种方式

    色相:将颜色用0°到360°表示,就是我们日常讲的颜色名称,如红色、蓝色等。


色相与颜色对应关系如上

    饱和度:色彩的纯度,饱和度越低色彩越暗淡(0<=S<1)

    明度:即颜色的明亮程度,数值越高越接近于白色,数值越低越接近于黑色(0<=V<1)

将图像从RGB色彩空间转换到HSV色彩空间的算法如下所示:

Max = max(R,G,B)

Min = min(R,G,B)


色相

饱和度: S = Max - Min

明度:V = Max

从HSV转换到RGB空间:


HSV——>RGB

# 上 BGR2HSV 和 HSV2BGR 代码

import cv2

import numpy as np

# BGR -> HSV

def BGR2HSV(_img):

    img = _img.copy() / 255.

    hsv = np.zeros_like(img, dtype=np.float32)

    # get max and min

    max_v = np.max(img, axis=2).copy()

    min_v = np.min(img, axis=2).copy()

    min_arg = np.argmin(img, axis=2)

    # H

    hsv[..., 0][np.where(max_v == min_v)]= 0

    ## if min == B

    ind = np.where(min_arg == 0)

    hsv[..., 0][ind] = 60 * (img[..., 1][ind] - img[..., 2][ind]) / (max_v[ind] - min_v[ind]) + 60

    ## if min == R

    ind = np.where(min_arg == 2)

    hsv[..., 0][ind] = 60 * (img[..., 0][ind] - img[..., 1][ind]) / (max_v[ind] - min_v[ind]) + 180

    ## if min == G

    ind = np.where(min_arg == 1)

    hsv[..., 0][ind] = 60 * (img[..., 2][ind] - img[..., 0][ind]) / (max_v[ind] - min_v[ind]) + 300

    # S

    hsv[..., 1] = max_v.copy() - min_v.copy()

    # V

    hsv[..., 2] = max_v.copy()

    return hsv

def HSV2BGR(_img, hsv):

    img = _img.copy() / 255.

    # get max and min

    max_v = np.max(img, axis=2).copy()

    min_v = np.min(img, axis=2).copy()

    out = np.zeros_like(img)

    H = hsv[..., 0]

    S = hsv[..., 1]

    V = hsv[..., 2]

    C = S

    H_ = H / 60.

    X = C * (1 - np.abs( H_ % 2 - 1))

    Z = np.zeros_like(H)

    vals = [[Z,X,C], [Z,C,X], [X,C,Z], [C,X,Z], [C,Z,X], [X,Z,C]]

    for i in range(6):

        ind = np.where((i <= H_) & (H_ < (i+1)))

        out[..., 0][ind] = (V - C)[ind] + vals[i][0][ind]

        out[..., 1][ind] = (V - C)[ind] + vals[i][1][ind]

        out[..., 2][ind] = (V - C)[ind] + vals[i][2][ind]

    out[np.where(max_v == min_v)] = 0

    out = np.clip(out, 0, 1)

    out = (out * 255).astype(np.uint8)

    return out

 


利用上述函数实现图像色相翻转(色相值+180,然后用 RGB色彩空间表示图片)

# Read image

img = cv2.imread("../paojie.jpg").astype(np.float32)

# RGB > HSV

hsv = BGR2HSV(img)

# Transpose Hue

hsv[..., 0] = (hsv[..., 0] + 180) % 360

# HSV > RGB

out = HSV2BGR(img, hsv)

# Save result

cv2.imwrite("out.jpg", out)

cv2.imshow("result", out)

cv2.waitKey(0)

cv2.destroyAllWindows()

 


 

原图


色相翻转后结果

参考:https://www.jianshu.com/p/9ff9d702ba9d