11 분 소요

“핸즈온 머신러닝”의 “10장 케라스를 사용한 인공신경망 소개” 파트를 읽고 공부한 내용을 정리해보았다. 케라스로 다층 퍼셉트론을 구현하는 방법을 다뤄볼 것이다.

10.2 케라스로 다층 퍼셉트론 구현하기

  • 케라스란

    • 모든 종류의 신경망을 손쉽게 만들도록, 훈련, 평가, 실행할 수 있는 고수준 딥러닝 API이다.

10.2.1 텐서플로 2 설치

# 버전 확인
import tensorflow as tf
from tensorflow import keras
tf.__version__, keras.__version__

두 번째 버전이 tf.keras에서 구현된 케라스의 API 버전이다.


10.2.2 시퀀셜 API를 사용하여 이미지 분류기 만들기

케라스를 사용하여 데이터셋 적재하기

# 패션 MNIST 적재하기
fashion_mnist = keras.datasets.fashion_mnist
(X_train_full, y_train_full), (X_test, y_test) = fashion_mnist.load_data()
# 훈련 세트이 크기와 데이터 타입 확인하기
X_train_full.shape, X_train_full.dtype
# 검증 데이터 셋 만들기
# 입력 데이터의 스케일 조정: 픽셀 강도를 255.0으로 나누어 0~1 사이 범위로 조정한다.
X_valid, X_train = X_train_full[:5000] / 255.0, X_train_full[5000:] / 255.0
y_valid, y_train = y_train_full[:5000], y_train_full[5000:]
X_test = X_test / 255.0
# 레이블에 해당하는 아이템 나타내기 위해 클래스 이름의 리스트 만들기
class_names = ["T-shirt", "Trouser", "Pullover", "Dress", "Coat", "Sandal", "Shirt", "Sneaker", "Bag", "Ankle boot"]
class_names[y_train[0]]


시퀀셜 API를 사용하여 모델 만들기

# 두 개의 은닉층으로 이루어진 분류용 다층 퍼셉트론
model = keras.models.Sequential()
model.add(keras.layers.Flatten(input_shape=[28, 28]))
model.add(keras.layers.Dense(300, activation='relu'))
model.add(keras.layers.Dense(100, activation='relu'))
model.add(keras.layers.Dense(10, activation='softmax'))

코드 설명

  • 첫 번째 라인은 Sequential 모델을 만든다. 순서대로 연결된 층을 일렬로 쌓아서 구성한다. (Sequential API)

  • 첫 번째 층을 만들고 모델에 추가한다. Flatten 층은 입력 이미지를 1차원 배열로 변환한다. 모델의 첫번 째 층이므로 input_shape을 지정해야한다.

  • 뉴런 300개를 가진 Dense 은닉층을 추가한다. ReLU 활성화 함수를 사용한다.

  • 뉴런 100개를 가진 두 번째 Dense 은닉층을 추가한다. ReLU 활성화 함수 사용한다.

  • 마지막 층인 뉴런 10개를 가진 Dense 출력층을 추가한다. 소프트맥스 활성화 함수를 사용한다.


# 위의 코드와 다른 버전
model = keras.models.Sequential([
    keras.layers.Flatten(input_shape=[28, 28]),
    keras.layers.Dense(300, activation='relu'),
    keras.layers.Dense(100, activation='relu'),
    keras.layers.Dense(10, activation='softmax')
])
# 모델에 있는 모든 층 출력하기
model.summary()
  • 첫번째 은닉층은 784x300개의 연결 가중치와 300개의 편향을 가진다. 즉 235500의 파라미터가 생성된다.

  • 이때 훈련 데이터가 많지 않은 경우, 과대 적합의 위험을 가진다.


# 모델에 있는 층을 리스트로 출력하거나 인덱스로 층을 선택할 수 있다.
model.layers
hidden1 = model.layers[1]
hidden1
hidden1.name
model.get_layer('dense_3') is hidden1
# 층의 모든 파라미터에 접근해보자
weights, biases = hidden1.get_weights()
weights, biases
weights.shape, biases.shape
  • Dense 층은 연결 가중치를 무작위로 초기화하고, 편향은 0으로 초기화한다.

  • 다른 초기화 방법은 11장에서 다루도록 한다.


모델 컴파일

  • 모델을 만든 후 사용할 손실 함수와 옵티마이저를 지정해야한다.

  • 또한 훈련과 평가 시에 계산할 지표를 추가로 지정할 수 있다.

model.compile(loss='sparse_categorical_crossentropy', 
              optimizer='sgd',
              metrics=['accuracy'])

코드 설명

  • 레이블이 정수 하나로 이루어져 있고, 클래스가 배타적일 때 “sparse_categorical_crossentropy” 손실을 사용한다.

  • 샘플마다 클래스별 타깃 확률을 가지고 있다면 “categorical_crossentropy” 손실을 사용해야한다.

  • 옵티마이저에 “sgd”를 지정하면 경사하강법을 이용하여 모델을 훈련한다는 의미이다. 즉, 역전파 알고리즘을 수행한다. 11장에서 더 효율적인 옵티마이저를 다뤄보자


모델 훈련과 평가

history = model.fit(X_train, y_train, epochs=30,
                    validation_data = (X_valid, y_valid))
  • 케라스는 에포크가 끝날 때마다 검증 세트를 사용해 손실과 추가적인 측정 지표를 계산한다.

  • 훈련 세트 성능이 검증 세트보다 월등히 높다면 모델이 과대적합되었을 것이다.

TIP

  • validation_data 매개변수에 검증 세트를 전달하는 대신 케라스가 검증에 사용할 훈련 세트의 비율을 지정할 수 있다.

  • validation_split=0.1로 쓰면 케라스는 섞기 전 훈련 데이터의 마지막 10%를 사용한다.

가중치 부여

  • 훈련 세트의 클래스가 편중되어 있다면 fit() 메서드를 호출할 때 class_weigth 매개변수를 지정하는 것이 좋다.

    • 적게 등장하는 클래스는 높은 가중치를 부여하고, 많이 등장하는 클래스는 낮은 가중치를 부여한다.
  • 샘플별로 가중치를 부여하고 싶다면 sample_weight 매개변수를 지정한다.

History 객체

  • 훈련 파라미터(history.params), 수행된 에포크(history.epoch)가 포함된다.

  • 딕셔너리 속성(history.history)

    • 훈련 세트와 검증 세트에 대한 손실과 측정한 지표를 담은 속성

    • 이 딕셔너리를 이용해 판다스 데이터 프레임을 만들고 plot() 메서드를 호출해서 학습 곡선을 볼 수 있다.

import pandas as pd
import matplotlib.pyplot as plt

pd.DataFrame(history.history).plot(figsize=(8, 5))
plt.grid(True)
plt.gca().set_ylim(0, 1) # 수직축의 범위를 0~1 사이로 설정
plt.show()

해석

  • 훈련하는 동안 훈련 정확도와 검증 정확도가 꾸준히 상승하는 것을 볼 수 있다.

  • 검증 곡선이 훈련 곡선과 가깝다. => 크게 과대적합되지 않았다.

  • 훈련 곡선을 볼 때 왼쪽으로 에포크의 절반만큼 이동해서 생각하기

    • 검증 손실은 에포크가 끝난 후에 계산되므로 훈련 손실 곡선은 에포크의 절반만큼 왼쪽으로 이동해야한다.
  • 검증 손실이 여전히 감소한다면 모델이 완전히 수렴되지 않아 훈련을 계속해야하는 의미이다.

  • 모델 성능이 만족스럽지 않으면 처음으로 되돌아가서 하이퍼 파라미터를 튜닝해야한다.

    1. 학습률 튜닝

    2. 다른 옵티마이저 테스트해보기

    3. 다시 1번으로

    4. 층 개수, 층의 뉴런 개수, 은닉층의 활성화 함수, 배치 크기 등 튜닝

  • 모델의 성능이 만족스럽다면 테스트 세트로 모델 평가하기

# 모델 평가
model.evaluate(X_test, y_test)
  • 테스트 세트에서는 하이퍼파라미터를 튜닝하려는 유혹을 참아야한다!!

  • 그렇지 않으면 일반화 오차를 제대로 추정할 수 없다.


모델을 사용해 예측을 만들기

# 새로운 샘플에 대해 예측 만들기
X_new = X_test[:3]
y_proba = model.predict(X_new)
y_proba.round(2)

코드 설명

  • 0에서 9까지 클래스마다 각각의 확률을 모델이 추정했다.
# 가장 높은 확률을 가진 클래스만 출력하기
y_pred = model.predict(X_new).argmax(axis=-1)
y_pred


10.2.3 시퀀셜 API를 사용하여 회귀용 다층 퍼셉트론 만들기

캘리포니아 주택 가격 데이터셋 적재하기

from sklearn.datasets import fetch_california_housing
from sklearn.model_selection import train_test_split
from sklearn.preprocessing import StandardScaler

housing = fetch_california_housing()

X_train_full, X_test, y_train_full, y_test = train_test_split(housing.data, housing.target)
X_train, X_valid, y_train, y_valid = train_test_split(X_train_full, y_train_full)

scaler = StandardScaler()
X_train = scaler.fit_transform(X_train)
X_valid = scaler.transform(X_valid)
X_test = scaler.transform(X_test)

분류와 차이점

  • 출력층이 활성화 함수가 없는 하나의 뉴런을 가진다.

  • 손실 함수로 평균 제곱 오차를 사용한다.

# 시퀀셜 API를 이용해 모델 만들기
model = keras.models.Sequential([
    keras.layers.Dense(30, activation='relu', input_shape=X_train.shape[1:]),
    keras.layers.Dense(1)
])

# 모델 컴파일
model.compile(loss="mean_squared_error",
              optimizer='sgd')
# 모델 훈련과 평가
history = model.fit(X_train, y_train, epochs=20,
              validation_data=(X_valid, y_valid))
mse_test = model.evaluate(X_test, y_test)

# 모델 예측하기
X_new = X_test[:3]
y_pred = model.predict(X_new)


결론

  • 시퀀셜 API는 사용하기 매우 쉽지만,

  • 입력과 출력이 여러 개이거나 더 복잡한 네트워크 토폴로지를 갖는 신경망을 만들어야할 때 함수형(functional) API를 사용한다.


10.2.4 함수형 API를 사용해 복잡한 모델 만들기

순차적이지 않은 신경망 (ex Wide & Deep 신경망)

  • 입력의 일부 또는 전체가 출력층에 바로 연결된다.

  • 신경망이 복잡한 패턴과 간단한 규칙을 모두 학습할 수 있다.


image

  • 순차적인 신경망 (일반적인 MLP)

    • 층 전체에 모든 데이터를 통과시키기 때문에 데이터에 있는 간단한 패턴이 연속된 변환으로 왜곡될 수 있다.
# 위 사진의 신경망 구현해보기
input_ = keras.layers.Input(shape=X_train.shape[1:])
hidden1 = keras.layers.Dense(30, activation='relu')(input_)
hidden2 = keras.layers.Dense(30, activation='relu')(hidden1)
concat = keras.layers.Concatenate()([input_, hidden2])
output = keras.layers.Dense(1)(concat)
model = keras.Model(inputs=[input_], outputs=[output])

코드 해석

  • Input 객체: shape과 dtype을 포함하여 모델의 입력을 정의한다. 여러 개의 입력을 가질 수 있다.

  • 30개의 뉴런과 ReLU 활성화 함수를 가진 Dense 층을 만든다. 이 층은 만들어지자마자 입력과 함께 함수처럼 호출된다. (함수형API로 불리는 이유)

  • 두 번째 은닉층을 만들고, 함수처럼 호출한다.

  • Concatenate() 함수를 호출하여 두 번째 은닉층의 출력과 입력을 연결한다.

  • 하나의 뉴런과 활성화 함수가 없는 출력층을 만들고 Concatenate 층이 만든 결과를 사용해 호출한다.

  • 마지막으로 사용할 입력과 출력을 지정하여 케라스 Model을 만든다.


또 다른 신경망

  • 일부 특성은 짧은 경로로 전달하고 다른 특성은 깊은 경로로 전달하고 싶다면?

    • 여러 입력을 사용하자


    image

input_A = keras.layers.Input(shape=[5], name='wide_input')
input_B = keras.layers.Input(shape=[6], name='deep_input')
hidden1 = keras.layers.Dense(30, activation='relu')(input_B)
hidden2 = keras.layers.Dense(30, activation='relu')(hidden1)
concat = keras.layers.Concatenate()([input_A, hidden2])
output = keras.layers.Dense(1)(concat)
model = keras.Model(inputs=[input_A, input_B], outputs=[output])
  • 모델 컴파일은 이전과 동일하지만 fit() 메서드를 호출할 때, 입력마다 하나씩 행렬의 튜플 (X_train_A, X_train_B)을 전달해야한다. X_valid, X_test, X_new에도 동일하게 적용된다.
model.compile(loss='mse', optimizer=keras.optimizers.SGD(learning_rate=1e-3))

X_train_A, X_train_B = X_train[:, :5], X_train[:, 2:]
X_valid_A, X_valid_B = X_valid[:, :5], X_valid[:, 2:]
X_test_A, X_test_B = X_test[:, :5], X_test[:, 2:]
X_new_A, X_new_B = X_test_A[:3], X_test_B[:3]

history = model.fit((X_train_A, X_train_B), y_train, epochs=20,
                    validation_data = ((X_valid_A, X_valid_B), y_valid))
mse_test = model.evaluate((X_test_A, X_test_B), y_test)
y_pred = model.predict((X_new_A, X_new_B))


여러 개의 출력이 필요한 경우

image

  • 그림에서 회귀 작업(물체 중심의 좌표와 너비, 높이를 찾는다)과 분류 작업을 함께하는 경우

  • 동일한 데이터에서 독립적인 여러 작업을 수행할 때 -> 다중 작업 분류 수행

  • 규제 기법으로 사용하는 경우

    • 과대 적합을 감소하고 모델의 일반화 성능을 높이도록 훈련에 제약을 가한다.

    • ex) 신경망 구조에 보조 출력을 추가한다. = 적절한 층에 연결하고 모델의 출력 리스트에 추가하면 된다.

# 보조 출력 추가한 모델 만들기 
input_A = keras.layers.Input(shape=[5], name='wide_input')
input_B = keras.layers.Input(shape=[6], name='deep_input')
hidden1 = keras.layers.Dense(30, activation='relu')(input_B)
hidden2 = keras.layers.Dense(30, activation='relu')(hidden1)
concat = keras.layers.Concatenate()([input_A, hidden2]) # 여기까지는 이전과 동일하다
output = keras.layers.Dense(1, name="main_output")(concat)
aux_output = keras.layers.Dense(1, name='aux_outout')(hidden2)
model = keras.Model(inputs=[input_A, input_B], outputs=[output, aux_output])
  • 각 출력은 자신만의 손실 함수 필요 => 컴파일할 때 손실의 리스트를 전달해야한다.

  • 케라스는 나열된 손실을 모두 더하여 최종 손실을 구해 훈련에 사용한다.

  • 또한 더 중요한 출력의 손실에 가중치를 부여할 수 있다.

# 컴파일 (+ 출력의 손실 가중치 지정)
model.compile(loss=['mse', 'mse'], loss_weights=[0.9, 0.1], optimizer='sgd')
# 모델 훈련
history = model.fit(
    [X_train_A, X_train_B], [y_train, y_train], epochs=20,
    validation_data=([X_valid_A, X_valid_B], [y_valid, y_valid])
)
# 결과: 개별 손실 & 총 손실 반환
total_loss, main_loss, aux_loss = model.evaluate(
    [X_test_A, X_test_B], [y_test, y_test]
)
# 각 출력에 대한 예측 반환하기
y_pred_main, y_pred_aux = model.predict([X_new_A, X_new_B])
y_pred_main, y_pred_aux


10.2.5 서브클래싱 API로 동적 모델 만들기

시퀀셜 API & 함수형 API

  • 선언적이다 => 사용할 층과 연결 방식을 먼저 정의해야하고 모델에 데이터를 주입하여 훈련/예측을 할 수 있다.

장점

  • 모델을 저장하거나 복사, 공유하기 쉽다.

  • 모델의 구조를 출력하거나 분석하기 쉽다

  • 모델에 데이터가 주입되기 전에 모델의 에러를 일찍 발견할 수 있다.

  • 정적이므로 디버깅하기 쉽다.

단점

  • 반복문을 포함하고 다양한 크기를 다루며, 조건문을 가지는 등 동적인 구조가 필요할 때가 많다. => 해결: 서브클래싱 API를 사용하면 된다!


# 서브클래싱 API로 동적 모델 만들기
class WideAndDeepModel(keras.Model):
  def __init__(self, units=30, activation='relu', **kwargs):
    super().__init__(**kwargs) # 표준 매개변수를 처리한다.
    self.hidden1 = keras.layers.Dense(units, activation=activation)
    self.hidden2 = keras.layers.Dense(units, activation=activation)
    self.main_output = keras.layers.Dense(1)
    self.aux_output = keras.layers.Dense(1)

  def call(self, inputs):
    input_A, input_B = inputs
    hidden1 = self.hidden1(input_B)
    hidden2 = self.hidden2(hidden1)
    concat = keras.layers.concatenate([input_A, hidden2])
    main_output = self.main_output(concat)
    aux_output = self.aux_output(hidden2)
    return main_output, aux_output

  model = WideAndDeepModel()

참고 - 파이썬 함수 선언부(*args, **kwargs)
args: 정해지지 않은 수의 (일반)파라미터 받음
kwargs: 정해지지 않은 수의 키워드 파라미터를 받는다. 키워드 파라미터 예시: Func(x=100, y=200, z=’b’)

코드 설명

  • 함수형 API와 유사하지만 Input객체를 만들지 않고 call() 메서드의 input 매개변수를 사용하였다.

  • 장점
    call() 메서드에서는 for, if문 등 원하는 계산이 가능하다. => 연구자에게 잘 맞는 API이다.

  • 단점
    모델 구조가 call() 메서드 안에 숨겨져있기 때문에 모델을 저장하거나 복사할 수 없다. => summary() 메서드를 호출하면 층의 목록만 나열되고 층 간의 연결 정보를 얻을 수 없다.
    타입과 크기를 미리 알 수 없어 실수가 발생할 수 있다.

=>따라서 일반적인 경우 (높은 유연성이 필요하지 않는다면) 시퀀셜 API와 함수형 API를 사용하는 것이 좋다.


10.2.6 모델 저장과 복원

지금까지 케라스를 사용하여 신경망을 만들고 훈련하는 법을 배웠다. 모델을 저장하는 법을 알아보자.

  • 저장 형식: HDF5 포맷 (.h5)

  • 저장 대상: 모델 구조와 층의 모든 모델 파라미터(연결 가중치, 편향), 옵티마이저를 저장한다.

  • 사용 방식: 하나의 파이썬 스크립트에서 모델을 훈련하고 저장한 다음 하나 이상의 스크립트(또는 웹)에서 모델을 로드하고 예측을 만드는데 활용한다.

# 시퀀셜 API를 이용해 모델 만들기
model = keras.models.Sequential([
    keras.layers.Dense(30, activation='relu', input_shape=X_train.shape[1:]),
    keras.layers.Dense(1)
])

# 모델 컴파일
model.compile(loss="mean_squared_error",
              optimizer='sgd')
# 모델 저장하기 => 간단 & 쉬움
model.save("my_keras_model.h5")
# 모델 로드하기
model = keras.models.load_model('my_keras_model.h5')

CAUTION
위의 모델 저장/로드 방식은 시퀀셜 API와 함수형 API에서만 사용가능하며 서브클래싱API에서는 사용 불가하다.


10.2.7 콜백 사용하기

훈련 도중 일정 간격으로 체크포인트를 저장하기 위해 콜백을 사용한다.

케라스가 훈련의 시작이나 끝 검증 또는 예측, 에포크의 시작이나 끝, 각 배치 처리 전후에 호출할 수 있다.

# ... 위에서 했던 방식대로 모델 만들고 컴파일 하기

# 체크포인트 저장하기
checkpoint_cb = keras.callbacks.ModelCheckpoint("my_keras_model.h5")
history = model.fit(X_train, y_train, epochs=10, callbacks=[checkpoint_cb])

save_best_only=True로 하면 최상의 검증 세트 점수에서만 모델을 저장한다. (단, 검증세트를 사용할 때!)

=> 과대적합 걱정 안해도 된다!


조기종료 첫 번째 방식

# 조기종료 방식1 & 최상의 모델 저장
checkpoint_cb = keras.callbacks.ModelCheckpoint("my_keras_model.h5", save_best_only=True)
history = model.fit(X_train, y_train, epochs=10,
                    validation_data = (X_valid, y_valid),
                    callbacks=[checkpoint_cb])
model = keras.models.load_model("my_keras_model.h5") # 저장된 최상의 모델로 복원


조기종료 두 번째 방식

  • EarlyStopping 콜백 사용한다. 일정 에포크동안 검증 세트에 대한 점수가 향상되지 않으면 훈련을 멈춘다.
    => 에포크의 숫자를 크게 지정해도 된다.

  • 선택적으로 최상의 모델을 복원할 수 있다.

  • 체크포인트 저장 콜백과 EarlyStopping 콜백 함께 사용 가능하다

  • 이전 코드이 경우와 다르게 훈련이 끝난 후 최상의 가중치를 복원해주기 때문에 저장된 모델을 따로 복원할 필요가 없다.

# 조기종료 방식2
early_stopping_cb = keras.callbacks.EarlyStopping(patioence=10, restore_best_weights=True)
history = model.fit(X_train, y_train, epochs=100,
                    validation_data=(X_valid, y_valid),
                    callbacks=[checkpoint_cb, early_stopping_cb])

그 밖에도 사용자 정의 콜백을 만들 수 있다.


사용자 정의 콜백

class PrintValTrainRatioCallback(keras.callbacks.Callback):
  def on_epoch_end(self, epoch, logs): # 메서드 이름 그대로 에포크가 끝날 때 호출한다
    print("\n val/train: {:.2f}".format(logs["val_loss"]/logs["loss"]))

코드 설명

훈련하는 동안 검증 손실과 훈련 손실의 비율 출력한다


10.2.8 텐서보드를 사용해 시각화하기

  • 훈련하는 동안 학습 곡선 그리기

  • 여러 실행 간의 학습 곡선 비교

  • 모델이 생성한 이미지 확인

  • 복잡한 다차원 데이터 시각화 & 자동 클러스터링 등 다양한 기능이 있다.

  • 텐서보드 서버: 로그 디렉터리를 모니터링하고 자동으로 변경사항을 읽어 그래프를 업데이트한다.

  • 데이터 기록 방식: 텐서서버가 루트 로그 디렉터리를 가리키고 서브 디렉터리에 이벤트를 기록한다.


위의 데이터 기록 방식을 구현해보자

import os
root_logdir = os.path.join(os.curdir, "my_logs") # 루트 디렉토리를 정의한다.

def get_run_logdir(): # 이벤트를 기록할 서브 디렉터리 생성
  import time
  run_id = time.strftime("run_%Y_%m_%d_%H_%M_%S")
  return os.path.join(root_logdir, run_id)

run_logdir = get_run_logdir()
### 이전과 같은 모델 구성과 컴파일
# 시퀀셜 API를 이용해 모델 만들기
model = keras.models.Sequential([
    keras.layers.Dense(30, activation='relu', input_shape=X_train.shape[1:]),
    keras.layers.Dense(1)
])

# 모델 컴파일
model.compile(loss="mean_squared_error",
              optimizer=keras.optimizers.SGD(learning_rate=0.001))

# 텐서보드 -> 로그 기록하기
tensorboard_cb = keras.callbacks.TensorBoard(run_logdir)
# 훈련
history = model.fit(X_train, y_train, epochs=30,
                    validation_data = (X_valid, y_valid),
                    callbacks=[tensorboard_cb])


learning_rate=0.05으로 두고 한번 더 실행해보자

run_logdir2 = get_run_logdir()

model2 = keras.models.Sequential([
    keras.layers.Dense(30, activation='relu', input_shape=X_train.shape[1:]),
    keras.layers.Dense(1)
])

# 모델 컴파일
model2.compile(loss="mean_squared_error",
              optimizer=keras.optimizers.SGD(learning_rate=0.05))

# 텐서보드 -> 로그 기록하기
tensorboard_cb = keras.callbacks.TensorBoard(run_logdir2)
# 훈련
history = model2.fit(X_train, y_train, epochs=30,
                    validation_data = (X_valid, y_valid),
                    callbacks=[tensorboard_cb])

코드 설명

위 코드를 실행하면 TensorBoard() 콜백이 로그 디렉터리를 생성한다. 훈련하는 동안 이벤트 파일을 만들고 서머리를 기록한다. (서머리: 시각화하려는 각각의 이진 데이터 레코드)

image
위와 같이 디렉토리와 파일이 생성된다.

  • my_logs - 루트 로그디렉터리

  • run_연도_월_일_시_분_초 - 서브디렉터리

  • train - 훈련 로그를 위한 서브디렉터리; 이벤트 파일, 프로파일링 트레이스 파일(모델의 각 부분에서 시간이 얼마나 소요되었는지 보여주는 요) 포함

  • validation - 검증 로그를 위한 서브디렉터리


텐서보드 서버를 실행해보자.

%load_ext tensorboard
%tensorboard --logdir=./my_logs --port=6006

실행 결과를 보면, lr = 0.05인 모델의 훈련 손실이 더 빠르게 감소한다.


텐서보드를 이용한 스칼라, 히스토그램, 이미지, 오디오, 텍스트 시각화

create_file_writer() 함수를 사용해 SummaryWriter를 만들고 with 블럭 안에서 텐서보드를 사용해 스칼라, 히스토그램, 이미지, 오디오, 텍스트를 기록하고 시각화해보자.

test_logdir = get_run_logdir()
writer = tf.summary.create_file_writer(test_logdir)
with writer.as_default():
  for step in range(1, 1000 + 1):
    tf.summary.scalar("my_scalar", np.sin(step/10), step=step)

    data = (np.random.randn(100)+2)*step/100
    tf.summary.histogram("my_hist", data, buckets=50, step=step)

    images = np.random.rand(2, 32, 32, 3) # 32x32 RGB 이미지
    tf.summary.image("my_images", images*step/1000, step=step)

    text = ["The step is"+str(step), "Its square is"+str(step**2)]
    tf.summary.text("my_text", text, step=step)

    sine_wave = tf.math.sin(tf.range(12000)/48000*2*np.pi*step)
    audio = tf.reshape(tf.cast(sine_wave, tf.float32), [1, -1, 1])
    tf.summary.audio("my_audio", audio, sample_rate=48000, step=step)
%load_ext tensorboard
%tensorboard --logdir=./my_logs --port=6006


배운 내용 요약

  • 신경망의 유래와 다츰 퍼셉트론의 개념

  • 분류와 회귀 문제를 위해 다층 퍼셉트론 사용하는 방법

  • 시퀀셜 API, 함수형 API, 서브클래싱 API 사용하는 방법

  • 모델 저장 & 복원

  • 콜백: 체크포인트 저장, 조기 종료 등

  • 텐서보드를 사용한 시각화 방법


지금까지 케라스 API를 사용하여 다층 퍼셉트론을 구현하는 방법에 대해 알아보았다. 다음 포스트에서는 신경망 하이퍼파라미터를 조정하여 모델의 성능을 높이는 방법을 다뤄볼 것이다.

댓글남기기