图像去噪与字典学习

在图像处理领域,去噪是一个重要的任务,它旨在减少图像中的噪声,恢复图像的原始特征。本文将介绍一种利用在线字典学习和多种变换方法对浣熊脸部图像碎片进行去噪的技术。首先,通过在线字典学习对图像的扭曲部分进行建模,然后利用该字典重建图像的另一部分。值得注意的是,如果从无噪声的图像开始,可能会获得更好的性能,但在这里假设这样的图像不可用。

评估图像去噪结果的常用方法是观察重建图像与原始图像之间的差异。如果重建完美,差异将呈现为高斯噪声。从图表中可以看出,使用正交匹配追踪(OMP)方法,保留两个非零系数的结果比仅保留一个系数的偏差要小(边缘看起来不那么突出)。此外,它在Frobenius范数上更接近真实值。最小角回归的结果则有更强的偏差:差异让人想起原始图像的局部强度值。阈值处理显然不适用于去噪,但在这里展示是为了说明它可以以非常高的速度产生有启发性的输出,因此可能适用于其他任务,如目标分类,其中性能不一定与可视化相关。

生成扭曲图像

import numpy as np try: # Scipy >= 1.10 from scipy.datasets import face except ImportError: from scipy.misc import face raccoon_face = face(gray=True) # 将uint8表示转换为0到1之间的浮点表示 raccoon_face = raccoon_face / 255.0 # 降采样以提高速度 raccoon_face = (raccoon_face[::4, ::4] + raccoon_face[1::4, ::4] + raccoon_face[::4, 1::4] + raccoon_face[1::4, 1::4]) / 4.0 height, width = raccoon_face.shape # 扭曲图像的右半部分 print("Distorting image...") distorted = raccoon_face.copy() distorted[:, width//2:] += 0.075 * np.random.randn(height, width//2) Distorting image...

接下来,将展示扭曲后的图像,并从中提取参考块。这些参考块将用于后续的字典学习过程。

显示扭曲图像

import matplotlib.pyplot as plt def show_with_diff(image, reference, title): ""“辅助函数用于显示去噪”"" plt.figure(figsize=(5, 3.3)) plt.subplot(1, 2, 1) plt.title("Image") plt.imshow(image, vmin=0, vmax=1, cmap=plt.cm.gray, interpolation="nearest") plt.xticks(()) plt.yticks(()) plt.subplot(1, 2, 2) difference = image - reference plt.title("Difference (norm: %.2f)" % np.sqrt(np.sum(difference**2))) plt.imshow(difference, vmin=-0.5, vmax=0.5, cmap=plt.cm.PuOr, interpolation="nearest") plt.xticks(()) plt.yticks(()) plt.suptitle(title, size=16) plt.subplots_adjust(0.02, 0.02, 0.98, 0.79, 0.02, 0.2) show_with_diff(distorted, raccoon_face, "Distorted image")

从图像的左半部分提取所有参考块,并对其进行标准化处理。这一步骤是为了确保字典学习过程的有效性。

from time import time from sklearn.feature_extraction.image import extract_patches_2d print("Extracting reference patches...") t0 = time() patch_size = (7, 7) data = extract_patches_2d(distorted[:, :width//2], patch_size) data = data.reshape(data.shape[0], -1) data -= np.mean(data, axis=0) data /= np.std(data, axis=0) print(f"{data.shape[0]} patches extracted in %.2fs." % (time() - t0)) Extracting reference patches... 22692 patches extracted in 0.03s.

现在,将使用这些参考块来学习字典。字典学习是一个无监督的过程,它旨在找到一组基础元素,这些元素可以有效地表示图像数据。

from sklearn.decomposition import MiniBatchDictionaryLearning print("Learning the dictionary...") t0 = time() dico = MiniBatchDictionaryLearning(n_components=50, batch_size=200, alpha=1.0, max_iter=10) V = dico.fit(data).components_ dt = time() - t0 print(f"{dico.n_iter_} iterations / {dico.n_steps_} steps in {dt:.2f}.")

学习完字典后,将使用它来重建图像的扭曲部分。这个过程涉及到从扭曲部分提取噪声块,然后使用字典对这些块进行变换和重建。

from sklearn.feature_extraction.image import reconstruct_from_patches_2d print("Extracting noisy patches... ") t0 = time() data = extract_patches_2d(distorted[:, width//2:], patch_size) data = data.reshape(data.shape[0], -1) intercept = np.mean(data, axis=0) data -= intercept print("done in %.2fs." % (time() - t0)) transform_algorithms = [ ("Orthogonal Matching Pursuit\n1 atom", "omp", {"transform_n_nonzero_coefs": 1}), ("Orthogonal Matching Pursuit\n2 atoms", "omp", {"transform_n_nonzero_coefs": 2}), ("Least-angle regression\n4 atoms", "lars", {"transform_n_nonzero_coefs": 4}), ("Thresholding\nalpha=0.1", "threshold", {"transform_alpha": 0.1}), ] reconstructions = {} for title, transform_algorithm, kwargs in transform_algorithms: print(title + "...") reconstructions[title] = raccoon_face.copy() t0 = time() dico.set_params(transform_algorithm=transform_algorithm, **kwargs) code = dico.transform(data) patches = np.dot(code, V) patches += intercept patches = patches.reshape(len(data), *patch_size) if transform_algorithm == "threshold": patches -= patches.min() patches /= patches.max() reconstructions[title][:, width//2:] = reconstruct_from_patches_2d(patches, (height, width//2)) dt = time() - t0 print("done in %.2fs." % dt) show_with_diff(reconstructions[title], raccoon_face, title + " (time: %.1fs)" % dt) plt.show()

通过上述步骤,可以看到不同去噪方法的效果。正交匹配追踪(OMP)和最小角回归(LARS)是两种常见的稀疏编码方法,它们在去噪方面表现出了不同的性能。阈值处理虽然不适用于去噪,但其高速的特点使其在其他任务中具有应用价值。

沪ICP备2024098111号-1
上海秋旦网络科技中心:上海市奉贤区金大公路8218号1幢 联系电话:17898875485