二、圖像二值化方法(python)---閾值全局固定、大津法


圖像二值化也叫做圖像閾值化處理,通過設定某個閾值爲門限,把多灰度級的圖像轉化爲僅僅有兩個極端的灰度級(0和255)。

閾值全局固定

利用python實現閾值全局固定時的二值化

import cv2
import matplotlib.pyplot as plt
import numpy as np
import math
import os
import pandas as pd
from tqdm import tqdm

image = cv2.imread("peng.png",0)
h = image.shape[0]
w = image.shape[1]

## 唯一確定閾值
a = 150
new_image = np.zeros((h,w),np.uint8)
for i in tqdm(range(h)):
    for j in range(w):
        if(image[i,j]> a ):
            new_image[i,j] = 255
        else:
            new_image[i,j] = 0

print(new_image)
cv2.imshow("new",new_image)
cv2.waitKey()

效果圖

在這裏插入圖片描述

大津法OTSU

  • 大津法又叫最大類間方差法、最大類間閾值法(OTSU)。
  • 它的基本思想是,用一個閾值將圖像中的數據分爲兩類,一類中圖像的像素點的灰度均小於這個閾值,另一類中的圖像的像素點的灰度均大於或者等於該閾值。如果這兩個類中像素點的灰度的方差越大,說明獲取到的閾值就是最佳的閾值。
  • 則利用該閾值可以將圖像分爲前景和背景兩個部分。而我們所感興趣的部分一般爲前景。

公式流程可自行百度。。。

利用Python實現大津法

import cv2
import os
import numpy as np
import pandas as pd
from tqdm import tqdm
### 首先將圖片轉化爲灰度圖像
image = cv2.imread("peng.png")
def rgb2gray(image):
    h = image.shape[0]
    w = image.shape[1]
    grayimage  = np.zeros((h,w),np.uint8)
    for i in tqdm(range(h)):
        for j in range(w):
            grayimage [i,j] = 0.144*image[i,j,0]+0.587*image[i,j,1]+0.299*image[i,j,1]
    return grayimage

### 大津法
def otsu(image):
    ### 高和寬
    h = image.shape[0]
    w = image.shape[1]
    ### 求總像素
    m = h*w

    otsuimg = np.zeros((h, w), np.uint8)
    ##初始閾值
    initial_threshold = 0
    ### 最終閾值
    final_threshold   = 0
    # 初始化各灰度級個數統計參數
    histogram = np.zeros(256, np.int32)
    # 初始化各灰度級佔圖像中的分佈的統計參數
    probability = np.zeros(256, np.float32)

    ### 各個灰度級的個數統計
    for i in tqdm(range(h)):
        for j in range(w):
            s = image[i,j]
            histogram[s] = histogram[s] +1
    ### 各灰度級佔圖像中的分佈的統計參數
    for i in tqdm(range(256)):
        probability[i] = histogram[i]/m

    for i in tqdm(range(255)):
        w0 = w1 = 0  ## 前景和背景的灰度數
        fgs = bgs = 0  # 定義前景像素點灰度級總和背景像素點灰度級總和
        for j in range(256):
            if j <= i:  # 當前i爲分割閾值
                w0 += probability[j]  # 前景像素點佔整幅圖像的比例累加
                fgs += j * probability[j]
            else:
                w1 += probability[j]  # 背景像素點佔整幅圖像的比例累加
                bgs += j * probability[j]
        u0 = fgs / w0  # 前景像素點的平均灰度
        u1 = bgs / w1  # 背景像素點的平均灰度
        G  = w0*w1*(u0-u1)**2
        if G >= initial_threshold:
            initial_threshold = G
            final_threshold = i
    print(final_threshold)

    for i in range(h):
        for j in range(w):
            if image[i, j] > final_threshold:
                otsuimg[i, j] = 255
            else:
                otsuimg[i, j] = 0
    return otsuimg

grayimage  = rgb2gray(image)
otsuimage  = otsu(grayimage)

cv2.imshow("grayimage",grayimage)
cv2.imshow("otsuimage",otsuimage)

cv2.waitKey()
# print(new_image)

效果圖如下

在這裏插入圖片描述

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章