生活随笔
收集整理的這篇文章主要介紹了
17-直方图
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
直方圖
何為直方圖?沒那么高大上,其實就是二維統計圖。每個照片都是有像素點所組成,當然也是[0,255],直方圖就是統計每個值所對應的像素點有幾個。
直方圖橫坐標表示0-255這些像素點值;縱坐標表示對應像素點值的個數有多少個,例如:像素為55的像素點有多少個
cv2.calcHist(images,channels,mask,histSize,ranges)
cv2.calcHist([img],[0],None,[256],[0,256])
參數一:images:原圖像格式為uint8或float32;當傳入函數時應該用中括號括住,通常情況下都是輸入的是灰度圖
參數二:同樣用中括號括起來,它會告訴函數我們圖像的直方圖;如果輸入圖像時灰度圖它的值就是[0];如果時彩色圖像傳入的參數可以是[0][1][2],分別對應BGR
參數三:掩模圖像,說白了就是取部分圖像而已;統計整個圖像的直方圖時就把它設置為None;當然也可以通過掩模來統計圖像的某部分的直方圖
參數四:BIN的數目,也就是橫坐標的總量程而已,一般都是256,也就是0-255這256個像素點值,也需要用中括號括起來
參數五:像素值的范圍,一般設置為[0,256]
import cv2
import numpy
as np
from matplotlib
import pyplot
as plt
def show_photo(name
,picture
):cv2
.imshow
(name
,picture
)cv2
.waitKey
(0)cv2
.destroyAllWindows
()img
= cv2
.imread
('E:\Jupyter_workspace\study\data/cat.png',0)
hist
= cv2
.calcHist
([img
],[0],None,[256],[0,256])
hist
.shapeplt
.hist
(img
.ravel
(),256)
plt
.show
()img
= cv2
.imread
('E:\Jupyter_workspace\study\data/cat.png')
color
= ('b','g','r')
for i
,col
in enumerate(color
):histr
= cv2
.calcHist
([img
],[i
],None,[256],[0,256])plt
.plot
(histr
,color
= col
)plt
.xlim
([0,256])
plt
.show
()
原圖:
原圖對應的灰度圖的直方圖:
原圖的BGR直方圖:
掩模mask
np.zeros(img.shape[:2],np.uint8)
上面的函數中有掩模的操作,接下來介紹一下掩模mask的定義的操作
import cv2
import numpy
as np
from matplotlib
import pyplot
as plt
def show_photo(name
,picture
):cv2
.imshow
(name
,picture
)cv2
.waitKey
(0)cv2
.destroyAllWindows
()
mask
= np
.zeros
(img
.shape
[:2],np
.uint8
)
print(mask
.shape
)
mask
[50:200,50:200] = 255
show_photo
('mask',mask
)img
= cv2
.imread
('E:\Jupyter_workspace\study\data/cat.png',0)
print(img
.shape
)
show_photo
('img',img
)masked_img
= cv2
.bitwise_and
(img
,img
,mask
=mask
)
show_photo
('masked_img',masked_img
)hist_full
= cv2
.calcHist
([img
],[0],None,[256],[0,256])
hist_mask
= cv2
.calcHist
([img
],[0],mask
,[256],[0,256])plt
.subplot
(221),plt
.imshow
(img
,'gray')
plt
.subplot
(222),plt
.imshow
(mask
,'gray')
plt
.subplot
(223),plt
.imshow
(masked_img
,'gray')
plt
.subplot
(224),plt
.plot
(hist_full
),plt
.plot
(hist_mask
)
plt
.xlim
([0,256])
plt
.show
()
掩模圖像:
原圖:
掩模操作后的圖像:
上一:原圖
上二:自定義的掩模
下一:掩模對應的原圖部分
下二:藍線對應原圖的直方圖,橙線對應掩模處理的部分原圖的直方圖
直方圖均衡化
假設某圖片部分像素值為:
|
| 255 | 128 | 200 | 50 |
| 50 | 200 | 255 | 50 |
| 255 | 200 | 128 | 128 |
| 200 | 200 | 255 | 50 |
下面表格中的函數映射中(255-0)表示設置的橫軸的量程這里設置的是0-255
灰度值像素個數概率累積概率根據函數映射后灰度值取整
| 50 | 4 | 4/16 = 0.25 | 0.25 | 0.25*(255-0)=63.75 | 64 |
| 128 | 3 | 3/16 = 0.1875 | 0.25+0.1875=0.4375 | 0.4375*(255-0)=111.5625 | 112 |
| 200 | 5 | 5/16 = 0.3125 | 0.25+0.1875+0.3125=0.75 | 0.75*(255-0)=191.25 | 191 |
| 255 | 4 | 4/16 = 0.25 | 0.25+0.1875+0.3125+0.25=1 | 1*(255-0)=255 | 255 |
均衡化后的像素值為:
|
| 255 | 112 | 191 | 64 |
| 64 | 191 | 255 | 64 |
| 255 | 191 | 112 | 112 |
| 192 | 191 | 255 | 255 |
均衡化之后發現了這16個數相差的并不是特別大了
cv2.equalizeHist(img)
傳入圖像對象名稱即可進行整體均衡化
import cv2
import numpy
as np
from matplotlib
import pyplot
as plt
def show_photo(name
,picture
):cv2
.imshow
(name
,picture
)cv2
.waitKey
(0)cv2
.destroyAllWindows
()img
= cv2
.imread
('E:\Jupyter_workspace\study\data/people.jpg',0)
plt
.hist
(img
.ravel
(),256)
plt
.show
()equ
= cv2
.equalizeHist
(img
)
plt
.hist
(equ
.ravel
(),256)
plt
.show
()res
= np
.hstack
((img
,equ
))
show_photo
('img_equ',res
)
原圖直方圖:
均衡化后的直方圖:
原圖和均衡化后的圖片對比:
均衡化后的圖像臉上的細節變得更加模糊了,尷尬不???
這時候就需要自定義均衡化
自定義均衡化
直方圖的均衡化也就是整體的均衡化,其他像素點值大的地方給平均給其他地方了導致一下細節會丟失
若將原圖分成塊進行均衡化,每塊進行自己塊的均衡化效果會比全局整體均衡化更好些
當然,若圖像里面噪音太大,局部反而沒有整體均衡化好,需要自己事先去衡量一下
cv2.createCLAHE(clipLimit = 2.0,tileGridSize = (8,8))
(8,8)表示分塊均衡化中塊的大小
import cv2
import numpy
as np
from matplotlib
import pyplot
as plt
def show_photo(name
,picture
):cv2
.imshow
(name
,picture
)cv2
.waitKey
(0)cv2
.destroyAllWindows
()img
= cv2
.imread
('E:\Jupyter_workspace\study\data/people.jpg',0)
plt
.hist
(img
.ravel
(),256)equ
= cv2
.equalizeHist
(img
)
plt
.hist
(equ
.ravel
(),256)clahe
= cv2
.createCLAHE
(clipLimit
= 2.0,tileGridSize
= (8,8))
res_clahe
= clahe
.apply(img
)res
= np
.hstack
((img
,equ
,res_clahe
))
show_photo
('img_equ_clahe',res
)
原圖-整體均衡化-自定義均衡化
總結
以上是生活随笔為你收集整理的17-直方图的全部內容,希望文章能夠幫你解決所遇到的問題。
如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。