??導向濾波(Guided Filter)是一種基于局部線性模型的濾波方法,用于圖像處理中的去噪、圖像增強和邊緣保留等任務。它結合了引導圖像(guide image)和輸入圖像來實現對輸入圖像的濾波操作。
原理
數學原理:
- 假設我們有一個引導圖像(guide image) I I I和一個輸入圖像(input image) P P P。
- 對于每個像素位置 i i i,我們想要計算輸出圖像 Q Q Q 中的像素值。
- 導向濾波的目標是學習一個線性模型來估計 Q i Q_i Qi?,使得 Q i = a i I i + b i Q_i = a_i I_i + b_i Qi?=ai?Ii?+bi?。
目標函數:
- 最小化目標函數 m i n a i , b i ∑ j ∈ N i ( a i I j + b i ? P j ) 2 + ? min_{a_i,b_i} \sum_{j \in \mathcal{N}_i} (a_i I_j + b_i - P_j)^2 + \epsilon minai?,bi??∑j∈Ni??(ai?Ij?+bi??Pj?)2+?,其中 N i \mathcal{N}_i Ni?是像素 i i i的鄰域, ? \epsilon ? 是一個較小的正則化參數。
線性方程求解:
- 對 a i a_i ai? 和 b i b_i bi?求偏導數,可以得到它們的閉式解:
a i = Cov ( I , P ) Var ( I ) + ? a_i = \frac{{\text{Cov}(I,P)}}{{\text{Var}(I) + \epsilon}} ai?=Var(I)+?Cov(I,P)?
b i = P i ˉ ? a i I i ˉ b_i = \bar{P_i} - a_i \bar{I_i} bi?=Pi?ˉ??ai?Ii?ˉ?
其中, Cov ( I , P ) \text{Cov}(I,P) Cov(I,P)是 I I I 和 P P P 的協方差, Var ( I ) \text{Var}(I) Var(I) 是 I I I的方差, I i ˉ \bar{I_i} Ii?ˉ?和 P i ˉ \bar{P_i} Pi?ˉ?分別是 I I I和 P P P在像素 i i i的均值。
作用和適用場景
- 去噪:導向濾波能有效地去除圖像中的噪聲,尤其是在保留邊緣信息的同時減少噪聲。
- 圖像增強:它能夠增強圖像的對比度和細節,使圖像更清晰、更鮮明。
- 邊緣保留:導向濾波可以保留圖像中的邊緣信息,在圖像處理中有助于保持邊緣的清晰度。
代碼示例
??在 Python 中,可以使用 OpenCV 庫來實現導向濾波。以下是一個簡單的示例代碼:
import cv2
import numpy as npdef guided_filter(I, P, radius, eps):mean_I = cv2.boxFilter(I, cv2.CV_64F, (radius, radius))mean_P = cv2.boxFilter(P, cv2.CV_64F, (radius, radius))mean_IP = cv2.boxFilter(I * P, cv2.CV_64F, (radius, radius))cov_IP = mean_IP - mean_I * mean_Pmean_II = cv2.boxFilter(I * I, cv2.CV_64F, (radius, radius))var_I = mean_II - mean_I * mean_Ia = cov_IP / (var_I + eps)b = mean_P - a * mean_Imean_a = cv2.boxFilter(a, cv2.CV_64F, (radius, radius))mean_b = cv2.boxFilter(b, cv2.CV_64F, (radius, radius))Q = mean_a * I + mean_breturn Q# 讀取圖像
input_image = cv2.imread('input_image.jpg', 0)
guide_image = cv2.imread('guide_image.jpg', 0)# 將圖像轉換為浮點數
input_image = np.float32(input_image) / 255.0
guide_image = np.float32(guide_image) / 255.0# 調用導向濾波函數
radius = 5
eps = 0.01
output_image = guided_filter(guide_image, input_image, radius, eps)# 顯示結果
cv2.imshow('Input Image', input_image)
cv2.imshow('Guide Image', guide_image)
cv2.imshow('Filtered Image', output_image)
cv2.waitKey(0)
cv2.destroyAllWindows()