Color Models (RGB, CMY, HSI)
Gonzalez R. C. and Woods R. E. Digital Image Processing (Forth Edition)
概
除了我们熟悉的RGB模式来表示图片, 还有其他很多种图片表示方式. 其实我现在很想要知道的一点是, 神经网络会对不同的表示会有不同的反应吗?
定义
RGB

普通的彩色图片, 每个像素点是一个三维的值\((x, y, z) \in [0, 1]^3\),
CMY
RGB是以Red, Green, Blue为坐标轴的坐标系, 而CMY是以Cyan, Magenta, Yellow为坐标轴(这些颜色成为second colors), 以White为原点的坐标系.
CMYK
CMY因为不是以black为原点, 所以在实际中难以表示true black? 所以特意引入第四个颜色K表示黑色.
HSI

HSI, 即hue, saturation, identisity.
Hue: 即表示某种颜色, 正如上图所示, 以H, 点与红色(标准)之间的角度(相当于指定某种颜色).
Saturation: 饱和度, 顾名思义, 表示该颜色是有多少的纯色和白色混合在一起的.
Identisity: 灰度值, 将一个图像变成一个灰度图就是根据这个指标, 其相当于\((x, y, z)\)在black-white这个轴上的投影.
注: HSI的值也是归一化为\([0, 1]\)之间.
相互的转换
RGB <=> CMY
\begin{array}{l}
C \\
M \\
Y \\
\end{array}
\right ] =
\left [
\begin{array}{l}
1 \\
1 \\
1 \\
\end{array}
\right ] -
\left [
\begin{array}{l}
R \\
G \\
B
\end{array}
\right ] .
\]
CMY <=> CMYK
CMY > CMYK
C = (C - K) / (1 - K), \\
M = (M - K) / (1 - K), \\
Y = (Y - K) / (1 - K). \\
\]
CMYK > CMY
M = M * (1 - K) + K, \\
Y = Y * (1 - K) + K. \\
\]
RGB <=> HSI
RGB > HSI
注意RGB > HSI并非直接的坐标变换, 具体的推导可以看上面的参考文献.
\{
\frac{\frac{1}{2}[(R-G) + (R-B)]}{[(R-G)^2 + (R-B)(G-B)]^{1/2}}
\}, \\
H =
\left \{
\begin{array}{ll}
\theta / 2\pi & \text{if} \: B \le G, \\
1 - \theta/2\pi & \text{if} \: B > G.
\end{array}
\right . \\
S = 1 - \frac{3}{R + G + B}[\min (R, G, B)]. \\
I = \frac{1}{3}(R + G + B).
\]
注: 原文使用的是角度制, 这里我改成弧度制, 另外我这里直接将\(H\)归一化了.
HSI > RGB
HSI > RGB 需要根据\(H\)的不同改变策略:
首先令\(H = H \cdot 2\pi \in [0, 2\pi)\).
- \(H \in [0, \frac{2}{3}\pi]\):
R = I[1 + \frac{S\cos H}{\cos (\frac{1}{3}\pi - H)}], \\
G = 3I - (R + B).
\]
- \(H \in [\frac{2}{3}\pi, \frac{4}{3}\pi)\):
R = I(1-S), \\
G = I[1 + \frac{S\cos H}{\cos (\frac{1}{3}\pi - H)}], \\
B = 3I - (R + G).
\]
- \(H \in [\frac{4}{3}\pi, 2\pi)\):
G = I(1-S), \\
B = I[1 + \frac{S\cos H}{\cos (\frac{1}{3}\pi - H)}], \\
R = 3I - (G + B).
\]
代码示例
import cv2
import matplotlib.pyplot as plt
import numpy as np
from PIL import Image
img = np.random.randint(0, 256, (10, 10, 3), dtype=np.uint8)
# rgb -> hsi
def calcH(v):
r, g, b = v
val = (2 * r - g - b) / np.sqrt((r - g) ** 2 + (r - b) * (g - b))
val /= 2
theta = np.arccos(val)
h = theta / (2 * np.pi) if b <= g else (1 - theta / (2 * np.pi))
return h
def calcS(v):
return 1 - 3 * v.min() / v.sum()
def calcI(v):
return v.mean()
def rgb2hsi(img: np.ndarray) -> np.ndarray:
img = img.astype(np.float) / 255.
def unit(v):
h = calcH(v)
s = calcS(v)
i = calcI(v)
return np.array([h, s, i])
img = np.apply_along_axis(unit, 2, img)
return img
# hsi -> rgb
def unit(v):
h, s, i = v
idx = np.arange(3)
h = h * np.pi * 2
if h >= 2 * np.pi / 3:
if h >= 4 * np.pi / 3:
h = h - 4 * np.pi / 3
idx = (idx - 2) % 3
else:
h = h - 2 * np.pi / 3
idx = (idx - 1) % 3
b = i * (1 - s)
r = i * (1 + s * np.cos(h) / np.cos(np.pi / 3 - h))
g = 3 * i - b - r
v = np.array([r, g, b])
return v[idx]
def hsi2rgb(img: np.ndarray):
img = img.astype(np.float) / 255.
img = np.apply_along_axis(unit, 2, img) * 255
return img.astype(np.uint8)
在opencv库中, 可以通过如下手段变化:
rgb2hsi_cv = cv2.cvtColor(img[..., [2, 1, 0]], cv2.COLOR_BGR2HLS)
hsi2rgb_cv = cv2.cvtColor(rgb2hsi_cv, cv2.COLOR_HLS2BGR)[..., [2, 1, 0]]
opencv采用BGR格式是由于历史原因.
另外, 其出来的结果和我所实现的结果并不一致, 其I值也并非\(\frac{1}{3}(R + G + B)\), 所以我怀疑可能用的是另外一套变换公式(虽然网上说, HLS就是HSI).
在PIL库中, 我没找到RGB2HSI的函数, 不过PIL一般采用如下方式进行变换:
rgb2what = Image.fromarray(img).convert('RGB').convert('...')
注: '...'部分表示mode, 具体参考: Concepts — Pillow (PIL Fork) 8.3.1 documentation
Color Models (RGB, CMY, HSI)的更多相关文章
- RGB to HSI, HSI to RGB Conversion Calculator
The RGB color model is an additive system in which each color is defined by the amount of red, green ...
- 常用icon以及color颜色RGB值和对应颜色效果图
Android谷歌官方扁平化设计常用icon集合 Android谷歌官方扁平化设计color颜色RGB值和对应颜色效果图.
- 基于RGB与HSI颜色模型的图像提取法
现实中我们要处理的往往是RGB彩色图像.对其主要通过HSI转换.分量色差等技术来提出目标. RGB分量灰度化: RGB可以分为R.G.B三分量.当R=G=B即为灰度图像,很多时候为了方便,会直接利用某 ...
- 【转载】颜色空间-RGB、HSI、HSV、YUV、YCbCr的简介
转载自缘佳荟的博客. 颜色通常用三个相对独立的属性来描述,三个独立变量综合作用,自然就构成一个空间坐标,这就是颜色空间.而颜色可以由不同的角度,用三个一组的不同属性加以描述,就产生了不同的颜色空间.但 ...
- QT 实现彩色图亮度均衡,RGB和HSI空间互相转换
从昨天折腾到今天.再折腾下去我都要上主楼了 大致和灰度图均衡是一样的,主要是不能像平滑什么的直接对R,G,B三个分量进行.这样出来的图像时没法看的.因此我们要对亮度进行均衡.而HSI彩色空间中的分量 ...
- COLORREF和COLOR和RGB的总结
一.COLORREF与RGB的相互转化 RGB(r,g,b)是一个宏 实际上它做得事是((COLORREF)(((BYTE)(r)|((WORD)((BYTE)(g))<<8))|(((D ...
- 实现RGB,CMY(K),YUV,YIQ,YCbCr颜色的转换算法
源:http://blog.sina.com.cn/s/blog_4d80055a01000atu.html import java.lang.Math; import java.awt.*; pub ...
- 颜色color转为rgb格式
function convertHexToRGB(color) { if (color.length === 4) { let extendedColor = &q ...
- RGB,CMYK,HSB各种颜色表示的转换 C#语言
Introduction Why an article on "colors"? It's the same question I asked myself before writ ...
随机推荐
- Spark(二十一)【SparkSQL读取Kudu,写入Kafka】
目录 SparkSQL读取Kudu,写出到Kafka 1. pom.xml 依赖 2.将KafkaProducer利用lazy val的方式进行包装, 创建KafkaSink 3.利用广播变量,将Ka ...
- 商业爬虫学习笔记day2
1. get传参 (1)url中包含中文报错解决方法 urllib.request.quote("包含中文的url", safe = "string.printtable ...
- 一起手写吧!call、apply、bind!
apply,call,bind都是js给函数内置的一些api,调用他们可以为函数指定this的执行,同时也可以传参. call call 接收多个参数,第一个为函数上下文也就是this,后边参数为函数 ...
- android Paint 详解
/** * Paint类介绍 * * Paint即画笔,在绘图过程中起到了极其重要的作用,画笔主要保存了颜色, * 样式等绘制信息,指定了如何绘制文本和图形,画笔对象有很多设置方法, * 大体 ...
- vue-cli 如何配置assetsPublicPath; vue.config.js如何更改assetsPublicPath配置;
问题: vue项目完成打包上线的时候遇到静态资源找不到的问题,网上很多解决办法都是基于vue-cli 2.x 来解决的,但从vue-cli 3.0以后,便舍弃了配置文件夹(便没有了config这个文件 ...
- 重量级&轻量级
重量级 就是说包的大小,还有就是与个人项目的耦合程度,重量级的框架与项目耦合程度大些 代表EJB容器的服务往往是"买一送三",不要都不行 轻量级 就是相对较小的包,当然与项目的耦合 ...
- feignclient发送get请求,传递参数为对象
feignclient发送get请求,传递参数为对象.此时不能使用在地址栏传递参数的方式,需要将参数放到请求体中. 第一步: 修改application.yml中配置feign发送请求使用apache ...
- Spring Boot对静态资源的映射规则
规则一:所有 " /webjars/** " 请求都去classpath:/META-INF/resources/webjars/找资源 webjars:以jar包的方式引入静态资 ...
- SpringMvc分析
1.用户单击某个请求路径,发起一个request请求,此请求会被前端控制器(DispatcherServlet)处理 2.前端控制器(DispatcherServlet)请求处理器映射器(Handle ...
- 1888-jerry99的数列--factorial
1 #define _CRT_SECURE_NO_WARNINGS 1//jerry99的数列 2 #include<bits/stdc++.h> 3 int prime[40000] = ...