天天看點

TensorFlow2實作去噪自編碼器(Denoising Autoencoder)去噪自編碼器(Denoising Autoencoder, DAE)DAE實作效果展示

去噪自編碼器(Denoising Autoencoder, DAE)

在介紹去噪自編碼器 (Denoising Autoencoder, DAE) 之前,首先介紹下DAE的一種使用場景示例,當我們在夜晚拍照時,或者其他黑暗環境時,我們的照片總是被大量的噪點所充斥,嚴重影響了圖像品質,而 DAE 的目的就是用來去除這些圖像中的噪聲。為了更好的講解 DAE,使用簡單的 MNIST 資料集進行示範,以将我們的重心放在有關 DAE 的知識上。如下圖所示,顯示了三組 MNIST 數字。每組的頂行是原始圖像 (Original Images);中間的行顯示 DAE 的輸入 (Noised Images),這些輸入是被噪聲破壞的原始圖像,當噪聲過多時,我們将很難讀懂被破壞的數字;最後一行顯示DAE的輸出 (Denoised Images)。

TensorFlow2實作去噪自編碼器(Denoising Autoencoder)去噪自編碼器(Denoising Autoencoder, DAE)DAE實作效果展示

Tips:如果對于自編碼器還不是很了解的話,可以參考

自編碼器模型詳解與實作(采用tensorflow2.x實作)

接下來就讓我們實際建構一個 DAE,以消除圖像中的噪聲。

DAE模型架構
TensorFlow2實作去噪自編碼器(Denoising Autoencoder)去噪自編碼器(Denoising Autoencoder, DAE)DAE實作效果展示

根據 DAE 的介紹可以将輸入定義為:

x = xorig + noise

其中 xorig 表示被噪聲 noise 破壞的原始 MNIST 圖像,編碼器的目的是學習潛矢量 z。DAE的損失函數表示為:

TensorFlow2實作去噪自編碼器(Denoising Autoencoder)去噪自編碼器(Denoising Autoencoder, DAE)DAE實作效果展示

其中,m 是輸出的次元,例如在MNIST資料集中,m=width × height×channels=28 × 28 × 1 = 784。xorigi 和 xi 分别是 xorig 和

TensorFlow2實作去噪自編碼器(Denoising Autoencoder)去噪自編碼器(Denoising Autoencoder, DAE)DAE實作效果展示

中的元素。

DAE實作

資料預處理

為了實作 DAE,首先需要構造訓練資料集,輸入資料是添加噪聲的 MNIST 數字,訓練輸出資料是原始的幹淨 MNIST 數字。添加的噪聲需要滿足高斯分布,均值 μ = 0.5,标準差 σ = 0.5。由于添加随機噪聲可能會産生小于0或大于1的無效像素值,是以需要将像素值裁剪為 [0.0,1.0] 範圍内。

# 資料加載
(x_train,_),(x_test,_) = keras.datasets.mnist.load_data()
# 資料預處理
image_size = x_train.shape[1]
x_train = np.reshape(x_train,[-1,image_size,image_size,1])
x_test = np.reshape(x_test,[-1,image_size,image_size,1])
x_train = x_train.astype('float32') / 255.
x_test = x_test.astype('float32') / 255.
# 産生高斯分布的噪聲
noise = np.random.normal(loc=0.5,scale=0.5,size=x_train.shape)
x_train_noisy = x_train + noise
noise = np.random.normal(loc=0.5,scale=0.5,size=x_test.shape)
x_test_noisy = x_test + noise
# 将像素值裁剪為[0.0,1.0]範圍内
x_train_noisy = np.clip(x_train_noisy,0.0,1.0)
x_test_noisy = np.clip(x_test_noisy,0.0,1.0)      

模型建構與模型訓練

#編碼器
inputs = keras.layers.Input(shape=input_shape,name='encoder_input')
x = inputs
for filters in layer_filters:
    x = keras.layers.Conv2D(filters=filters,
            kernel_size=kernel_size,
            strides=2,
            activation='relu',
            padding='same')(x)
shape = keras.backend.int_shape(x)
x = keras.layers.Flatten()(x)
latent = keras.layers.Dense(latent_dim,name='latent_vector')(x)
encoder = keras.Model(inputs,latent,name='encoder')
# 解碼器
latent_inputs = keras.layers.Input(shape=(latent_dim,),name='decoder_input')
x = keras.layers.Dense(shape[1]*shape[2]*shape[3])(latent_inputs)
x = keras.layers.Reshape((shape[1],shape[2],shape[3]))(x)
for filters in layer_filters[::-1]:
    x = keras.layers.Conv2DTranspose(filters=filters,
            kernel_size=kernel_size,
            strides=2,
            padding='same',
            activation='relu')(x)
outputs = keras.layers.Conv2DTranspose(filters=1,
        kernel_size=kernel_size,
        padding='same',
        activation='sigmoid',
        name='decoder_output')(x)
decoder = keras.Model(latent_inputs,outputs,name='decoder')
autoencoder = keras.Model(inputs,decoder(encoder(inputs)),name='autoencoder')
# 模型編譯與訓練
autoencoder.compile(loss='mse',optimizer='adam')
autoencoder.fit(x_train_noisy,
        x_train,validation_data=(x_test_noisy,x_test),
        epochs=10,
        batch_size=batch_size)
# 模型測試
x_decoded = autoencoder.predict(x_test_noisy)      

效果展示
TensorFlow2實作去噪自編碼器(Denoising Autoencoder)去噪自編碼器(Denoising Autoencoder, DAE)DAE實作效果展示

如上圖所示,當噪聲水準從 σ=0.5 增加到 σ=0.75 和 σ=1.0 時,DAE 具有一定的魯棒性,可以較好的恢複出原始圖像。但是,在 σ=1.0 時,某些數字,沒有被正确地恢複。