OpenCV—python颜⾊直⽅图与直⽅图均衡化⽂章⽬录
⼀、颜⾊直⽅图
1.1 使⽤opencv展⽰直⽅图
函数 cv2.calcHist(image,channels,mask,histSize,ranges) -> list
image: array为待计算直⽅图的图像
channels:list 通道,RGB图像可以指定[0,1,2],灰度图像只有[0],
mask 掩码,可以指定图像的范围,如果是全图,默认为none
hitsize 为直⽅图的灰度级数,例如[0,255]⼀共256级
range 为像素值范围,为[0,255]
下⾯三个函数功能在RGB图像处理下差不多,请⾃⾏查阅资料
np.histogram()
np.bincount()
cv2.calcHist()
import cv2
import numpy as np
def calcAndDrawHist(image, color):
hist= cv2.calcHist([image],[0],None,[256],[0.0,255.0])
minVal, maxVal, minLoc, maxLoc = cv2.minMaxLoc(hist)
histImg = np.zeros([256,256,3], np.uint8)
hpt =int(0.9*256);
for h in range(256):
intensity =int(hist[h]*hpt/maxVal)
cv2.line(histImg,(h,256),(h,256-intensity), color)
return histImg
if __name__ =='__main__':
original_img = cv2.imread("666.png")
b, g, r = cv2.split(img)
histImgB = calcAndDrawHist(b,[255,0,0])
histImgG = calcAndDrawHist(g,[0,255,0])
histImgR = calcAndDrawHist(r,[0,0,255])
cv2.imshow("histImgB", histImgB)
cv2.imshow("histImgG", histImgG)
cv2.imshow("histImgR", histImgR)
cv2.imshow("Img", img)
cv2.waitKey(0)
cv2.destroyAllWindows()
1.2 使⽤matplotlib 绘制
matplotlib.pyplot.plot(hist,color)进⾏绘制
plt.hist(img.ravel(),hitsizes,ranges,color=)img.ravel()将原图像的array数组转成⼀维的数组
hitsizes 为直⽅图的灰度级数
ranges 为灰度范围[0,255]
color 使⽤color=’'来指定颜⾊
展⽰⽅法:
hist = cv2.calcHist ([res ],[0],None ,[256],[0,255])
plt .plot (hist ,'r')
plt .show ()
=======================================================
plt .hist (res .ravel (), 256, [0, 256],color ='r')
plt .show ()
⼆、直⽅图均衡化
为什么要进⾏直⽅图均衡化呢?我们⽇常拍照时,背对太阳时或晚上出现图像⽋曝,⾯对太阳拍照会出现过曝,图像均衡可以通过图像直⽅图均衡来调整图像,也可以通过 校正,来校正图⽚。
γ
图像的直⽅图是对图像对⽐度效果上的⼀种处理,旨在使得图像整体效果均匀,⿊与⽩之间的各个像素级之间的点更均匀⼀点。亮度可以更好地在直⽅图上分布。这样就可以⽤于增强局部的对⽐度⽽不影响整体的对⽐度,直⽅图均衡化通过有效地扩展常⽤的亮度来实现这种功能。(直接效果展⽰)
cv2.equalizeHist(img) 均衡化的原图像【输⼊img:单通道图像】则返回值即为均衡化后的图像。
2.1 全局直⽅图均衡化与⾃适应均衡化
import cv2
import numpy as np
img = cv2.imread('0002.jpg',0)
img1 = cv2.equalizeHist(img)# 全局直⽅图均衡化
clahe = ateCLAHE(clipLimit=2.0,tileGridSize=(8,8))# ⾃适应直⽅图均衡化
cll = clahe.apply(img)
res = np.hstack((img,img1,cll))
cv2.imwrite("res.jpg",res)
显然全局直⽅图均衡化效果不好,造成部分过曝,部分细节消失。
如下图:依次是原图;全局直⽅图均衡化;⾃适应直⽅图均衡化
2.2 使⽤查表来拉伸直⽅图
在图像处理中,直⽅图均衡化⼀般⽤来均衡图像的强度,或增加图像的对⽐度。
观察上图中原始图像的直⽅图,很容易发现⼤部分强度值范围都没有⽤到。
因此先检测图像⾮0的最低(imin)强度值和最⾼(imax)强度值。
将最低值imin设为0,最⾼值imax设为255。中间的按255.0*(i-imin)/(imax-imin)+0.5)的形式设置。
lut = np.zeros(256, dtype = image.dtype )#创建空的查表
hist,bins = np.histogram(image.flatten(),256,[0,256])
cdf = hist.cumsum()#计算累积直⽅图
cdf_m = np.ma.masked_equal(cdf,0)#除去直⽅图中的0值
cdf_m =(cdf_m - cdf_m.min())*255/(cdf_m.max()-cdf_m.min())#等同于前⾯介绍的lut[i] = int(255.0 *p[i])公式cdf = np.ma.filled(cdf_m,0).astype('uint8')#将掩模处理掉的元素补为0
#计算
result2 = cdf[image]
result = cv2.LUT(image, cdf)
cv2.imshow("OpenCVLUT", result)
cv2.imshow("NumPyLUT", result2)
cv2.waitKey(0)
cv2.destroyAllWindows()
lut = np.zeros(256, dtype = image.dtype )# 创建空的查表
hist= cv2.calcHist([image],[0],None,[256],[0.0,255.0])
minBinNo, maxBinNo =0,255局部直方图均衡化
for binNo, binValue in enumerate(hist):#计算从左起第⼀个不为0的直⽅图柱的位置
if binValue !=0:
minBinNo = binNo
break
for binNo, binValue in enumerate(reversed(hist)):#计算从右起第⼀个不为0的直⽅图柱的位置
if binValue !=0:
maxBinNo =255-binNo
break
print(minBinNo, maxBinNo)
for i,v in enumerate(lut):#⽣成查表,⽅法来⾃参考⽂献1第四章第2节
print(i)
if i < minBinNo:
lut[i]=0
elif i > maxBinNo:
lut[i]=255
else:
lut[i]=int(255.0*(i-minBinNo)/(maxBinNo-minBinNo)+0.5)
#计算
result = cv2.LUT(image, lut)
cv2.imshow("hist", hist)
cv2.imshow("Result", result)
cv2.waitKey(0)
cv2.destroyAllWindows()
2.3 直⽅图均衡化—RGB2YCrCb
⽅法:将RGB彩⾊图像先转换到YPbPr空间,然后只对亮度通道进⾏全局直⽅图均衡化和⾃适应直⽅图均衡化,最后再将亮度通道和PbPr 通道合并形成彩⾊图像,然后再转换回RGB空间中。
代码详细:/4.1.0/d5/daf/tutorial_py_histogram_equalization.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论