[OpenCV][Python]fastNlMeansDenoising非局部均值濾波

閱讀時間約 1 分鐘

cv2.fastNlMeansDenoising() 是 OpenCV 中一個非常有效的去噪函數,基於非局部均值濾波算法(Non-Local Means Filtering)。它能夠有效地去除圖像中的隨機噪聲(如高斯噪聲),並保留圖像的細節,特別適合處理含有隨機噪聲的圖像。

這個函數的主要特點是能夠根據像素周圍的鄰域進行濾波,而不僅僅依賴局部的像素值,因此可以在去除噪聲的同時,保留圖像的細節

fastNlMeansDenoising結果圖

raw-image

調用方式

cv2.fastNlMeansDenoising() 函數的使用格式如下:

cv2.fastNlMeansDenoising(src, dst=None, h=3, templateWindowSize=7, searchWindowSize=21)
  • src: 輸入的單通道圖像(灰度圖像)。
  • dst: 輸出的圖像(可以設為 None,表示輸出結果覆蓋原圖)。
  • h: 決定去噪的強度,值越高去噪越強,但可能會丟失更多細節。
  • templateWindowSize: 鄰域大小,通常設為奇數(默認為 7)。
  • searchWindowSize: 檢索窗口大小,越大會增加計算量,但效果更好(默認為 21)。

實作範例程式碼

import cv2
import numpy as np
import matplotlib.pyplot as plt

# 讀取原始圖像
img = cv2.imread('lena.png', 0) # 讀取灰度圖像

# 添加高斯噪聲到圖像
noise = np.random.normal(0, 25, img.shape).astype(np.uint8) # 創建高斯噪聲
noisy_img = cv2.add(img, noise) # 將噪聲加入到原始圖像

# 使用fastNlMeansDenoising進行去噪
denoised_img = cv2.fastNlMeansDenoising(noisy_img, None, h=10, templateWindowSize=7, searchWindowSize=21)

# 顯示結果
plt.figure(figsize=(12, 6))

# 顯示原始圖像
plt.subplot(1, 3, 1)
plt.imshow(img, cmap='gray')
plt.title("原始圖像")
plt.axis('off')

# 顯示加噪聲的圖像
plt.subplot(1, 3, 2)
plt.imshow(noisy_img, cmap='gray')
plt.title("加噪聲圖像")
plt.axis('off')

# 顯示去噪後的圖像
plt.subplot(1, 3, 3)
plt.imshow(denoised_img, cmap='gray')
plt.title("去噪後圖像")
plt.axis('off')

plt.show()

結果分析

  • 原始圖像:這是最初沒有任何噪聲的圖像。
  • 加噪聲圖像:在原始圖像上添加了隨機的高斯噪聲,這種噪聲在拍攝過程中可能因為感光元件的問題產生,導致圖像質量下降。
  • 去噪後圖像:通過 cv2.fastNlMeansDenoising() 去除了隨機噪聲,保留了圖像的大部分細節。


參數說明

  • h(強度參數):這個參數控制去噪的強度,較大的值會去掉更多的噪聲,但可能會損失更多細節。如果你的圖像噪聲較少,推薦設置較小的 h 值。
  • templateWindowSize:這是計算非局部均值時的模板窗口大小,通常設為奇數,值越大對結果的影響也越大。
  • searchWindowSize:這個窗口決定了在模板窗口之外搜尋類似區域的範圍。較大的搜尋窗口通常能夠產生更好的結果,但運行速度會變慢。


與其他濾波器比較

import cv2
import numpy as np
import matplotlib.pyplot as plt

# 讀取原始圖像
img = cv2.imread('輸入圖像', 0) # 讀取灰度圖像

# kernel 調整
kernel = 11
# 添加高斯噪聲到圖像
noise = np.random.normal(0, 25, img.shape).astype(np.uint8) # 創建高斯噪聲
noisy_img = cv2.add(img, noise) # 將噪聲加入到原始圖像

# 1. 使用fastNlMeansDenoising進行去噪
denoised_img_nlmeans = cv2.fastNlMeansDenoising(noisy_img, None, h=45, templateWindowSize=9, searchWindowSize=21)

# 2. 使用均值濾波進行去噪
denoised_img_mean = cv2.blur(noisy_img, (kernel, kernel))

# 3. 使用高斯濾波進行去噪
denoised_img_gaussian = cv2.GaussianBlur(noisy_img, (kernel, kernel), 0)

# 4. 使用中值濾波進行去噪
denoised_img_median = cv2.medianBlur(noisy_img, kernel)

# 5. 使用雙邊濾波進行去噪
denoised_img_bilateral = cv2.bilateralFilter(noisy_img, 9, 75, 75)

# 顯示結果
plt.figure(figsize=(18, 12))

plt.rcParams['font.sans-serif'] = ['Microsoft YaHei'] # 中文字體
plt.rcParams['axes.unicode_minus'] = False # 解決座標軸負號顯示問題

# 顯示加噪聲的圖像
plt.subplot(2, 3, 1)
plt.imshow(noisy_img, cmap='gray')
plt.title("加噪聲圖像")
plt.axis('off')

# 顯示fastNlMeansDenoising的去噪結果
plt.subplot(2, 3, 2)
plt.imshow(denoised_img_nlmeans, cmap='gray')
plt.title("非局部均值去噪")
plt.axis('off')

# 顯示均值濾波去噪結果
plt.subplot(2, 3, 3)
plt.imshow(denoised_img_mean, cmap='gray')
plt.title("均值濾波去噪")
plt.axis('off')

# 顯示高斯濾波去噪結果
plt.subplot(2, 3, 4)
plt.imshow(denoised_img_gaussian, cmap='gray')
plt.title("高斯濾波去噪")
plt.axis('off')

# 顯示中值濾波去噪結果
plt.subplot(2, 3, 5)
plt.imshow(denoised_img_median, cmap='gray')
plt.title("中值濾波去噪")
plt.axis('off')

# 顯示雙邊濾波去噪結果
plt.subplot(2, 3, 6)
plt.imshow(denoised_img_bilateral, cmap='gray')
plt.title("雙邊濾波去噪")
plt.axis('off')

plt.tight_layout()
plt.show()


比較結果圖

raw-image


總結

raw-image

1. 均值濾波 (Mean Filtering)

  • 原理:均值濾波是一種線性濾波器,將窗口內的像素值取平均,並將該平均值賦予窗口中心的像素點。
  • 適用場景
    • 適合處理輕度隨機噪聲。
    • 對於圖像邊緣保護能力較弱,會導致圖像模糊。
    • 常用於需要快速消除輕微噪聲的場景,如數據預處理、平滑圖像。
  • 缺點:會模糊邊緣和細節,特別不適合應用於邊緣敏感的圖像。

2. 高斯濾波 (Gaussian Filtering)

  • 原理:高斯濾波對像素周圍的鄰域加權平均,權重由距離像素的高斯分佈決定。距離中心越近的像素權重大。
  • 適用場景
    • 適合處理高斯噪聲(如感光器產生的隨機噪聲)。
    • 用於影像去噪的同時需要保持一定的平滑度。
    • 經常用於圖像模糊處理、邊緣檢測前的平滑。
  • 缺點:雖然保留了更多的圖像細節,但仍然可能造成邊緣模糊。

3. 中值濾波 (Median Filtering)

  • 原理:中值濾波是一種非線性濾波方法,對窗口內的像素進行排序,並將中值賦予窗口中心的像素點。
  • 適用場景
    • 非常適合處理椒鹽噪聲(Salt-and-Pepper Noise)。
    • 用於需要去除孤立噪聲點的情況,且在保護圖像邊緣方面表現良好。
    • 適用於圖像處理中的許多場合,如醫學圖像處理和衛星圖像去噪。
  • 缺點:對於大範圍的隨機噪聲效果不如高斯濾波或其他方法,且處理速度相對較慢。

4. 雙邊濾波 (Bilateral Filtering)

  • 原理:雙邊濾波結合空間鄰域的距離與像素值的差異來進行加權平均,從而在去除噪聲的同時保留邊緣。
  • 適用場景
    • 適合需要去除噪聲但同時保留圖像邊緣和細節的場景,如照片去噪、精細影像處理等。
    • 常用於去噪與保持邊緣的平衡場景,如人像照片後期處理。
  • 缺點:計算量較大,處理速度慢,不適合實時應用。

5. 非局部均值去噪 (Non-Local Means Denoising)

  • 原理:基於圖像的自相似性,搜尋圖像的各個區域中相似的區塊進行加權平均。這使得它在保留細節的同時能很好地去除噪聲。
  • 適用場景
    • 適合處理高斯噪聲和隨機噪聲,特別是在需要保留圖像細節的情況下,如高質量照片和影像處理。
    • 在醫學影像處理、顯微圖像處理、攝影後期等細節要求高的場景中使用。
  • 缺點:運行速度慢,適用於非實時的去噪應用。



116會員
182內容數
本業是影像辨識軟體開發,閒暇時間進修AI相關內容,將學習到的內容寫成文章分享。
留言0
查看全部
發表第一個留言支持創作者!
螃蟹_crab的沙龍 的其他內容
當影像中有雜訊時,使用直方圖均衡化來增強對比就會受雜訊的影響,從而影響到整體的結果。應對這個問題,可以考慮使用自適應直方圖均衡化來減少雜訊的影響,並增強對比度。 本文將比較直方圖均衡化與自適應直方圖均衡化的差異性。 [OpenCV基礎][Python]影像增強_直方圖均衡處理 直方圖均衡化的
在 OpenCV 中,將圖片從 BGR 色彩空間轉換為灰階圖像時常用cv2.COLOR_BGR2GRAY ,此函數使用了特定的權重來計算灰階值。這些權重是基於人眼對不同顏色的敏感度進行調整的。 Gray=0.299×R+0.587×G+0.114×B 本文介紹了用其他方式來提取色彩通道
cv2.countNonZero 是 OpenCV 中的一個函數,用來計算二值圖像(或單通道圖像)中非零像素的數量。這個函數對於圖像處理中的許多操作非常有用,例如計算某個區域內的白色像素數量,從而幫助我們了解圖像的內容或進行進一步的分析。 使用範例 假設您有一個二值圖像,其中白色像素
局部二值化(Local Thresholding)是一種影像處理技術,用來根據局部區域的像素值動態地將影像轉換為二值影像。這在處理光照不均勻的影像時特別有用。 與常見的兩種二值化(Otsu's與固定閥值)方法做比較。 實現局部二值化的範例: import cv2 import numpy
在某些特殊情況下,需要將圖片進行黑白反轉,例如Tesseract(OCR辨識引擎)就有建議黑底白字的狀況下辨識率較高。 本文將使用 NumPy 進行影像黑白反轉,並顯示反轉前後的影像。
常見的圖像銳利化方法: 銳化濾波器 增強對比度 Unsharp Masking
當影像中有雜訊時,使用直方圖均衡化來增強對比就會受雜訊的影響,從而影響到整體的結果。應對這個問題,可以考慮使用自適應直方圖均衡化來減少雜訊的影響,並增強對比度。 本文將比較直方圖均衡化與自適應直方圖均衡化的差異性。 [OpenCV基礎][Python]影像增強_直方圖均衡處理 直方圖均衡化的
在 OpenCV 中,將圖片從 BGR 色彩空間轉換為灰階圖像時常用cv2.COLOR_BGR2GRAY ,此函數使用了特定的權重來計算灰階值。這些權重是基於人眼對不同顏色的敏感度進行調整的。 Gray=0.299×R+0.587×G+0.114×B 本文介紹了用其他方式來提取色彩通道
cv2.countNonZero 是 OpenCV 中的一個函數,用來計算二值圖像(或單通道圖像)中非零像素的數量。這個函數對於圖像處理中的許多操作非常有用,例如計算某個區域內的白色像素數量,從而幫助我們了解圖像的內容或進行進一步的分析。 使用範例 假設您有一個二值圖像,其中白色像素
局部二值化(Local Thresholding)是一種影像處理技術,用來根據局部區域的像素值動態地將影像轉換為二值影像。這在處理光照不均勻的影像時特別有用。 與常見的兩種二值化(Otsu's與固定閥值)方法做比較。 實現局部二值化的範例: import cv2 import numpy
在某些特殊情況下,需要將圖片進行黑白反轉,例如Tesseract(OCR辨識引擎)就有建議黑底白字的狀況下辨識率較高。 本文將使用 NumPy 進行影像黑白反轉,並顯示反轉前後的影像。
常見的圖像銳利化方法: 銳化濾波器 增強對比度 Unsharp Masking
你可能也想看
Google News 追蹤
Thumbnail
本專欄將提供給您最新的市場資訊、產業研究、交易心法、精選公司介紹,以上內容並非個股分析,還請各位依據自身狀況作出交易決策。歡迎訂閱支持我,獲得相關內容,也祝您的投資之路順遂! 每年 $990 訂閱方案👉 https://reurl.cc/VNYVxZ 每月 $99 訂閱方案👉https://re
Thumbnail
呈上篇文章,針對單排的圖像文字增加間隔,但如果文字是雙排呢 [OpenCV][Python]OCR分割及增加間隔[單排文字]
Thumbnail
在影像辨識中,若遇到物件與背景難以分辨的狀況下,先做一下色彩分析,知道了色彩強度階層上的像素數,有助於了解後續需要做什麼處理,比較好分割出辨識物。 若想辨識的物件與背景的RGB值過於接近,也比較好說明此狀況,為什麼較難分割出物件。 成果呈現 第一張圖:左邊為原圖,右邊為分析結果的圖,用其他顏
Thumbnail
常見的圖像銳利化方法: 銳化濾波器 增強對比度 Unsharp Masking
Thumbnail
形態學操作在影像處理中有多種應用,特別是在處理二值化影像(黑白影像)。 在影像處理應用上,基本上都由侵蝕,膨脹這兩種方法,組合搭配而成。 常見應用場景 物體檢測與分割: 形態學操作可以用於增強或改善二值化影像中的物體邊界,使得物體的檢測和分割更加準確。
Thumbnail
本文將介紹影像的基本操作包括:影像的讀取、顯示、保存,以及一些常見的操作如裁剪、旋轉、縮放等。 語法介紹 讀取影像: cv2.imread函數的參數是影像的檔案路徑。讀取後的影像以NumPy的ndarray形式表示。
Thumbnail
OpenCV(Open Source Computer Vision Library)是一個開源的計算機視覺和影像處理庫,它提供了豐富的功能和工具,可用於開發各種視覺應用程式。 OpenCV最初是用C++編寫的,但它也提供了Python、Java等多種程式語言的接口,方便不同語言的開發者使用。
Thumbnail
本文介紹OpenCV中的SimpleBlobDetector用於檢測斑點或圓,以及其與霍夫轉換找圓方法的差異。透過程式範例和解析,講解檢測到的關鍵點和設定參數,並整理SimpleBlobDetector與霍夫轉換的不同。最後,探討不同的應用場景和參數調整。
Thumbnail
本文將利用OpenCV的findContours函式,從找到的輪廓中來計算物件的面積,周長,邊界框等屬性,從而得到物體的寬度與高度。 一般來說,我們在進行輪廓檢測時,會先進行圖像二值化,將對象轉換為白色,背景為黑色。這樣,在找到輪廓後,輪廓的點就會以白色表示,背景為黑色。 結果圖 從圖中綠色框
Thumbnail
[影像處理_OpenCV Python]使用Python撰寫影像處理功能,圖片遮罩或濾除掉不要的地方,旋轉圖片 以下範例將呈現影像處理三種不同的應用: 遮罩的實現 濾除 旋轉
Thumbnail
本專欄將提供給您最新的市場資訊、產業研究、交易心法、精選公司介紹,以上內容並非個股分析,還請各位依據自身狀況作出交易決策。歡迎訂閱支持我,獲得相關內容,也祝您的投資之路順遂! 每年 $990 訂閱方案👉 https://reurl.cc/VNYVxZ 每月 $99 訂閱方案👉https://re
Thumbnail
呈上篇文章,針對單排的圖像文字增加間隔,但如果文字是雙排呢 [OpenCV][Python]OCR分割及增加間隔[單排文字]
Thumbnail
在影像辨識中,若遇到物件與背景難以分辨的狀況下,先做一下色彩分析,知道了色彩強度階層上的像素數,有助於了解後續需要做什麼處理,比較好分割出辨識物。 若想辨識的物件與背景的RGB值過於接近,也比較好說明此狀況,為什麼較難分割出物件。 成果呈現 第一張圖:左邊為原圖,右邊為分析結果的圖,用其他顏
Thumbnail
常見的圖像銳利化方法: 銳化濾波器 增強對比度 Unsharp Masking
Thumbnail
形態學操作在影像處理中有多種應用,特別是在處理二值化影像(黑白影像)。 在影像處理應用上,基本上都由侵蝕,膨脹這兩種方法,組合搭配而成。 常見應用場景 物體檢測與分割: 形態學操作可以用於增強或改善二值化影像中的物體邊界,使得物體的檢測和分割更加準確。
Thumbnail
本文將介紹影像的基本操作包括:影像的讀取、顯示、保存,以及一些常見的操作如裁剪、旋轉、縮放等。 語法介紹 讀取影像: cv2.imread函數的參數是影像的檔案路徑。讀取後的影像以NumPy的ndarray形式表示。
Thumbnail
OpenCV(Open Source Computer Vision Library)是一個開源的計算機視覺和影像處理庫,它提供了豐富的功能和工具,可用於開發各種視覺應用程式。 OpenCV最初是用C++編寫的,但它也提供了Python、Java等多種程式語言的接口,方便不同語言的開發者使用。
Thumbnail
本文介紹OpenCV中的SimpleBlobDetector用於檢測斑點或圓,以及其與霍夫轉換找圓方法的差異。透過程式範例和解析,講解檢測到的關鍵點和設定參數,並整理SimpleBlobDetector與霍夫轉換的不同。最後,探討不同的應用場景和參數調整。
Thumbnail
本文將利用OpenCV的findContours函式,從找到的輪廓中來計算物件的面積,周長,邊界框等屬性,從而得到物體的寬度與高度。 一般來說,我們在進行輪廓檢測時,會先進行圖像二值化,將對象轉換為白色,背景為黑色。這樣,在找到輪廓後,輪廓的點就會以白色表示,背景為黑色。 結果圖 從圖中綠色框
Thumbnail
[影像處理_OpenCV Python]使用Python撰寫影像處理功能,圖片遮罩或濾除掉不要的地方,旋轉圖片 以下範例將呈現影像處理三種不同的應用: 遮罩的實現 濾除 旋轉