导向滤波与opencv python实现

定义

导向滤波是一个线性滤波,输出为由引导图 I I I乘上输入图 P P P得到的权重的加权平均。
在这里插入图片描述
i i i j j j是像素下标,滤波核 W i j W_{ij} Wij I I I的函数,其不依赖于 p p p

引导滤波器的关键假设是引导I和滤波器输出 q q q之间的局部线性模型。我们假设 q q q I I I在以像素 k k k为中心的窗口 ω k \omega_k ωk中的线性变换。
在这里插入图片描述
这里假设( a k a_k ak, b k b_k bk)在 ω k \omega_k ωk中为线性的常数。其中 ω k \omega_k ωk为一个半径为 r r r的正方形窗口。在一个窗口 ω k \omega_k ωk内,只会确定一个 a k a_k ak b k b_k bk,但可以根据一个 a k a_k ak b k b_k bk,求出 ∣ ω ∣ |\omega| ω q i q_i qi。这个局部线性模型确保 q q q只有在 I I I有边缘时才有边缘,因为 ∇ q ∇q q = a ∇ I a∇I aI

推导

利用岭回归确认参数 a k a_k ak, b k b_k bk的值,也就是求下式的最小值:
在这里插入图片描述
其中 ϵ \epsilon ϵ是一个正则化参数,以防 a k a_k ak过大。
可以认为 q i q_i qi p i p_i pi去掉噪音 n i n_i ni后的图片:
在这里插入图片描述

得出的结果如下:
在这里插入图片描述
其中 μ k \mu_k μk σ k 2 \sigma_k^2 σk2 I I I ω k \omega_k ωk内的均值与方差。 ∣ ω ∣ |\omega| ω是窗口内的像素数目。 p ‾ k \overline{p}_k pk是窗口内 p p p的均值。具体推导可参考:公式推导

将这个线性模型应用在整幅图像上的所有小窗口上, q i q_i qi在不同的小窗口内会有不同取值,所以需要将 q i q_i qi取平均:
在这里插入图片描述
论文指出,一开始提出的加权平均的权重如下式:
在这里插入图片描述
其只取决于引导图像 I I I。具体推导详见论文3.3。

ϵ \epsilon ϵ值的影响

I = p I=p I=p时,该算法即成为一个边缘保持滤波器。
在这里插入图片描述

Case 1:

如果某个窗口在平坦区域,那么该区域的方程 σ k 2 \sigma_k^2 σk2将远远小于 ϵ \epsilon ϵ。从而 a k ≈ 0 a_k\approx0 ak0 b k ≈ p ‾ k b_k\approx\overline{p}_k bkpk,即相当于对该区域作均值滤波。

Case 2:

如果某个窗口在高方差区域,那么该区域的方程 σ k 2 \sigma_k^2 σk2将远远大于 ϵ \epsilon ϵ。从而 a k ≈ 1 a_k\approx1 ak1 b k ≈ 0 b_k\approx0 bk0,即相当于在区域保持原有梯度。

在这里插入图片描述
r r r ϵ \epsilon ϵ越大,图像越模糊,越趋于做均值滤波。

代码

在这里插入图片描述
输入图像必须得先进行归一化后再处理,否则滤波后会有超过255的值

def guided_filter(I,p,win_size,eps):

    mean_I = cv2.blur(I,(win_size,win_size))
    mean_p = cv2.blur(p,(win_size,win_size))

    corr_I = cv2.blur(I*I,(win_size,win_size))
    corr_Ip = cv2.blur(I*p,(win_size,win_size))

    var_I = corr_I-mean_I*mean_I
    cov_Ip = corr_Ip - mean_I*mean_p

    a = cov_Ip/(var_I+eps)
    b = mean_p-a*mean_I

    mean_a = cv2.blur(a,(win_size,win_size))
    mean_b = cv2.blur(b,(win_size,win_size))

    q = mean_a*I + mean_b
    return q

参考文献

Guided Image Filtering
导向滤波(Guided Filter)公式详解

猜你喜欢

转载自blog.csdn.net/qtzbxjg/article/details/127267133
今日推荐