본문 바로가기
딥러닝

autoencoder에 대해서 - (2) 코드

by 제리의 세계 2023. 5. 19.

안녕하세요! 제리입니다.

autoencoder를 fashion_mnist 데이터를 통해 tensorflow로 표현해보도록 하겠습니다.

참고는 이 유튜브를 참고했습니다.

https://www.youtube.com/watch?v=0PqWUsKPZdQ

  • 라이브러리 불러오기
import tensorflow as tf
from tensorflow.keras.datasets import fashion_mnist
from tensorflow.keras.models import Model
from tensorflow.keras.layers import Dense, Flatten,Reshape
from tensorflow.keras.losses import MeanSquaredError
import numpy as np
import matplotlib.pyplot as plt
plt.style.use('seaborn-white')
  • 데이터 불러오기
# 이미지 데이터만 가져오기
(x_train,_), (x_test,_) = fashion_mnist.load_data()

# normalize 해주기
x_train = x_train.astype('float32')/255.
x_test = x_test.astype('float32')/255.

print(x_train.shape) --(60000, 28, 28)
print(x_test.shape) --(10000, 28, 28)
  • 모델 정의하여 만들기
latent_dim = 64

class Autoencoder(Model):
  def __init__(self, latent_dim):
    super(Autoencoder, self).__init__()

    self.latent_dim = latent_dim
    # 784차원에서 64차원으로 압축
    self.encoder = tf.keras.Sequential([Flatten(), Dense(latent_dim, activation = 'relu')])
    # 압축된 것을 다시 재구성
    self.decoder = tf.keras.Sequential([Dense(784, activation = 'sigmoid'), Reshape((28,28))])
  
  def call(self, x):
    encoded = self.encoder(x)
    decoded = self.decoder(encoded)
    return decoded
    
autoencoder = Autoencoder(latent_dim)
autoencoder.compile(optimizer = 'adam', loss = MeanSquaredError())
  • 모델 학습시키기
# 원본 입력 값을 넣어주고 출력 값도 원본 값과 유사하게 나오는지 보기 위함이므로 x_train과 x_train을 fit에 넣어주는 것.
autoencoder.fit(x_train,x_train, epochs = 10, shuffle = True, validation_data = (x_test,x_test))
  • 모델 테스트하기
    encoded_imgs = autoencoder.encoder(x_test).numpy()
    decoded_imgs = autoencoder.decoder(encoded_imgs).numpy()
    
    n = 10
    plt.figure(figsize = (20,4))
    
    # 원본 값과 재구성한 값을 보여주기 
    for i in range(n):
      ax = plt.subplot(2, n, i+1)
      plt.imshow(x_test[i])
      plt.title('original')
      plt.gray()
      ax.get_xaxis().set_visible(False)
      ax.get_yaxis().set_visible(False)
    
      ax = plt.subplot(2, n, i+1+n)
      plt.imshow(decoded_imgs[i])
      plt.title('reconstructed')
      plt.gray()
      ax.get_xaxis().set_visible(False)
      ax.get_yaxis().set_visible(False)
    
    plt.show()

똑같이 fashion mnist 사용하지만 pytorch를 사용해서 작성해보기

참고한 자료는 이곳! https://dacon.io/codeshare/4551

 

  • 라이브러리와 데이터 불러오기
import torch
import torchvision
import torch.nn.functional as F
from torch import nn, optim
from torchvision import transforms, datasets

import matplotlib.pyplot as plt
import numpy as np

batch_size = 64

# fashion mnist 데이터셋 설정
trainset = datasets.FashionMNIST(root= './.data/', train = True, download = True, transform = transforms.ToTensor())
train_loader = torch.utils.data.DataLoader(
    dataset = trainset,
    batch_size = batch_size,
    shuffle = True,
    num_workers = 2
)
  • 모델 설정하기
class Autoencoder(nn.Module):
  def __init__(self):
    super(Autoencoder, self).__init__()
# 입력 데이터 사이즈인 28*28에서 줄여나간다.
    self.encoder = nn.Sequential(
        nn.Linear(28*28,128),
        nn.ReLU(),
        nn.Linear(128,64),
        nn.ReLU(),
        nn.Linear(64,12),
        nn.ReLU(),
        nn.Linear(12,3) # 여기에서는 3차원까지 압축 => latent vector
    )
# 3차원까지 줄였던 것을 재구성하기 위해 다시 복원
    self.decoder = nn.Sequential(
        nn.Linear(3,12),
        nn.ReLU(),
        nn.Linear(12,64),
        nn.ReLU(),
        nn.Linear(64,128),
        nn.ReLU(),
        nn.Linear(128,28*28),
        nn.Sigmoid() # 픽셀당 0,1 값 출력하는 시그모이드 함수 추가
    )
  def forward(self, x):
    encoded = self.encoder(x) #잠재 변수
    decoded = self.decoder(encoded) #복원 이미지
    return encoded, decoded
  • 파라미터 정의하기
autoencoder = Autoencoder()
optimizer = torch.optim.Adam(autoencoder.parameters(), lr = 0.005)
criterion = nn.MSELoss()
  • 모델 훈련시키기
def train(autoencoder, train_loader):
  autoencoder.train()
  for step, (x, label) in enumerate(train_loader):
    x = x.view(-1, 28*28)
    y = x.view(-1, 28*28)
    label = label

    encoded, decoded = autoencoder(x)

    loss = criterion(decoded, y)
    optimizer.zero_grad()
    loss.backward()
    optimizer.step()
  • 모델 학습시켜 이미지 시각화하기
# 학습시키기
Epoch = 10
for epoch in range(1, Epoch+1): #위에서 epoch를 10으로 설정
  train(autoencoder, train_loader)
  test_x = view_data
  _, decoded_data = autoencoder(test_x)

  f,a = plt.subplots(2,5, figsize = (5,2))
  print("[Epoch {}]".format(epoch))
# 원본 데이터 시각화하기
  for i in range(5):
    img = np.reshape(view_data.data.numpy()[i],(28,28))
    a[0][i].imshow(img, cmap = 'gray')
    a[0][i].set_xticks(()); a[0][i].set_yticks(())
# 재구성한 이미지 시각화하기
  for i in range(5):
    img = np.reshape(decoded_data.data.numpy()[i],(28,28))
    a[1][i].imshow(img,cmap = 'gray')
    a[1][i].set_xticks(()); a[1][i].set_yticks(())
  plt.show()