본문 바로가기
프로그램

[파이썬] Bilateral Filter기반의 Time-series Denoising(노이즈 제거)

by 오디세이99 2023. 7. 18.
728x90
반응형

Gaussian Filter를 적용할 때, edge가 뭉개지는 문제점이 있음. 

Bilateral 필터는 이미지 또는 신호 처리에서 노이즈 제거에 사용되는 비선형 필터입니다. 이 필터는 두 가지 가중치 함수를 사용하여 노이즈를 제거하고 윤곽을 보존합니다. Bilateral 필터는 공간적 가중치와 강도 가중치를 동시에 고려하여 노이즈를 제거합니다.

공간적 가중치는 주변 픽셀의 거리에 따라 계산됩니다. 두 픽셀 간의 거리가 가까울수록 더 높은 가중치를 갖게 됩니다. 이로써 픽셀의 주변 픽셀들에 대해서만 영향을 받는다는 것을 의미합니다. 이 공간적 가중치는 가우시안 함수로 계산됩니다.

강도 가중치는 중심 픽셀과 주변 픽셀 간의 값 차이에 따라 계산됩니다. 두 픽셀 값이 비슷할수록 더 높은 가중치를 갖게 됩니다. 이로써 픽셀 값이 유사한 주변 픽셀들에 대해서만 영향을 받는다는 것을 의미합니다. 강도 가중치는 가우시안 함수로 계산되며, 강도 차이에 대한 표준 편차를 설정하여 조절할 수 있습니다.

Bilateral 필터는 공간적 가중치와 강도 가중치를 곱한 후, 주변 픽셀 값에 적용하여 중심 픽셀 값을 계산합니다. 이렇게 계산된 중심 픽셀 값은 노이즈가 제거된 결과이며, 원본 이미지나 신호의 윤곽을 보존하는 특징이 있습니다.

Bilateral 필터는 노이즈 제거 외에도 엣지 보존, 텍스처 보존 등에도 사용될 수 있으며, 다양한 영상 처리 및 컴퓨터 비전 응용에 널리 사용되는 필터 중 하나입니다.

import cv2
import numpy as np
from sklearn.preprocessing import MinMaxScaler
import matplotlib.pyplot as plt

# Generate clean sine wave
data_size = 2000  # Increased data size
t = np.linspace(0, 10, data_size)
clean_data = np.sin(t)

# Add uniform noise
noise = np.random.uniform(-0.1, 0.1, data_size)
noisy_data = clean_data + noise

# Normalize data
scaler = MinMaxScaler(feature_range=(0, 1))  # Normalization to [0, 1]
noisy_data = scaler.fit_transform(noisy_data.reshape(-1, 1))

# Reshape the data to a 2D array (necessary for the convolutional autoencoder)
noisy_data = noisy_data.reshape((-1, 1))

# Convert data to 8-bit
noisy_data_8bit = (noisy_data * 255).astype(np.uint8)

# Apply bilateral filter for noise removal
# filtered_data_8bit = cv2.bilateralFilter(noisy_data_8bit, -1, 0.5, 5)
filtered_data_8bit = cv2.bilateralFilter(noisy_data_8bit, -1, 30, 100)

# Rescale filtered data back to the original range
filtered_data = (filtered_data_8bit / 255.0).reshape(-1, 1)

# Reshape filtered data back to 1D array
filtered_data = filtered_data.flatten()

# Plotting
plt.figure(figsize=(10, 6))
plt.plot(t, clean_data, label='Clean Data')
plt.plot(t, noisy_data, label='Noisy Data')
plt.plot(t, filtered_data, label='Filtered Data')
plt.title('Bilateral Filter for Noise Removal')
plt.xlabel('Time')
plt.ylabel('Amplitude')
plt.legend()
plt.show()

728x90
반응형

댓글