Non-local Mean 图像去噪算法的基本实现(Python)
最近开始做视频去噪方面的工作,无一例外就会看到NLM这种经典的基于块匹配图像去噪算法。
那么最最基本的NLM算法所涉及的公式如下所示:
为加深对公式的理解,写了个python版本的NLM,内含6个循环,没有做任何算法上的优化,没有矩阵运算,什么都没有,效率极低。
def imnlmeans_naive(img, sigma, s1, s2, p1,p2, h):
# backup
img_out = np.zeros((img.shape[0],img.shape[1]))
# padding
pad = int((s1+s2)/2 + (p1+p2)/2)
img_pad = np.lib.pad(img, pad, 'symmetric')
# plt.imshow(img_pad, cmap=plt.cm.gray)
# plt.show()
hight = img.shape[0]
width = img.shape[1]
P = (2*p1+1)*(2*p2+1)
patch = 0
patch2 = 0
Z = 0
for i in range(s1+p1,hight+s1+p1+1):
for j in range(s2+p2,width+s2+p2+1):
for i1 in range(i-s1,i+s1+1):
for j1 in range(j-s2,j+s2+1):
for i2 in range(i1-p1,i1+p1+1):
for j2 in range(j1-p2,j1+p2+1):
patch = patch + (img_pad[i2,j2] - img_pad[i2+p1+s1,j1+p2+s2])**2
patch = patch / P
f = fai(patch, sigma, h, P)
patch2 = patch2 + f*img_pad[i1,j1]
Z = Z + f
img_out[i-s1-p1,j-s2-p2] = 1.0/Z*patch2
return img_out
接下来会放出NLM优化后的python代码,以及NLM的改进算法,即基于块(Block-wise NL-means)的NLM。
图像去噪的东西才刚刚接触,所以有些词语、说法会不准确,还请大家指出不足、不准确之处,谢谢。