openCV简要-05 直方图

1.绘制直方图
一个图像的每个像素点的值都在0 ~ 255,统计图像中0 ~ 255各出现了多少次,以此绘制分布图

import cv2
import numpy as np
import matplotlib.pyplot as plt

img=cv2.imread('test.jpg',0)#0表示以灰度图格式读入
hist=cv2.calcHist([img],[0],None,[256],[0,256])
#函数原型:calcHist(src,channels,mask,histSize,range)
#src为输入图像,要以列表形式传参
#channel为通道;对于灰度图为[0],对于彩色图,B为[0],G为[1],R为[2]。
#mask为掩模图像,即只对图像中的某一部分统计次数绘制分布图
#histSize为横轴区间长度,[256]表示横轴坐标为0、1、2、···、255
#range为像素取值范围,一般是[0,256]
print(hist.shape)#查看直方图属性(256,1)

plt.hist(img.ravel(),256)#numpy的ravel()方法是将多维数组降为一维数组
plt.show()
#显示直方图

#绘制彩色图的直方图
img=cv2.imread('ccat.jpg')
color=('b','g','r')
for i,col in enumerate(color):
	hist=cv2.calcHist([img],[i],None,[256],[0,256])
	plt.plot(hist,color=col)
	plt.xlim([0,256])#xlim指定直方图plt制图x轴范围
plt.show()

#mask操作
mask=np.zeros(img.shape[:2],np.uint8)#不考虑通道,只需要二维
mask[100:300,100:400]=255#使一部分变白
cv2.imshow('mask',mask)#观察效果

masked_img=cv2.bitwise_and(img,img,mask=mask)
#原型bitwise_and(src1,src2,mask)表示src1和src2与运算后用mask掩膜处理

#使用掩膜后的直方图对比
hist_mask=cv2.calcHist([img],[0],mask,[256],[0,256])
hist_full=cv2.calcHist([img],[0],None,[256],[0,256])

plt.subplot(221),plt.imshow(img,'original')
plt.subplot(222),plt.imshow(mask,'mask')
plt.subplot(223),plt.imshow(masked_img,'masked')
plt.subplot(224),plt.plot(hist_full),plt(hist_mask)
plt.xlim([0,256])
plt.show()

2.直方图均衡化
直方图有时呈现出某一区间很集中的情况,但期望它变得平滑一些
直接的效果是图像的对比度提高(直方图均衡化可以提高图像的对比度)

对于某个像素值x,在图像中的像素个数为n个,则x出现的概率是:n/总像素数;累积概率(递推式)为:(x-1)像素的累积概率+x的概率;经过映射:新灰度值=累积概率*像素最大取值(255),然后四舍五入取整。

import cv2
import numpy as np
import matplotlib.pyplot as plt

img=cv2.imread('test.jpg',0)
equ=cv2.equalizeHist(img)#直方图均衡化
plt.hist(equ.ravel(),256)
plt.show()

3.自适应直方图均衡化
整体图像进行直方图均衡化会造成细节丢失(本身对比度较高的地方会被平均到其他位置,导致原图像对比度较高的地方变得太“亮”)我们希望这些地方不要被均衡化;使用自适应直方图均衡化,将图像分为几个块,块内进行均衡化,openCV的该方法还会对分块的边界部分进行插值处理,使均衡化的图像不会明显地表现出分块边界线。

import cv2
import numpy as np
import matplotlib.pyplot as plt

img=cv2.imread('test.jpg',0)
#生成一个自适应均衡化方法
clahe=cv2.createCLAHE(clipLimit=2.0,tileGridSize=(8,8))
#将图像按该方法适应
img_clahe=clahe.apply(img)
res=np.hstack((img,img_clahe))
cv2.imshow('res',res)
cv2.waitKey(0)
cv2.destroyAllWindow()

Guess you like

Origin blog.csdn.net/qq_43579980/article/details/113179982