개발 교육 일기

파이썬 교육 Day 41(+ 신경망 출력층 설계, 신경망의 사용처, 소프트맥스 함수 구현, softmax의 특징, 소프트맥스 함수 튜닝, 출력층의 뉴런 수 정하기, MNIST 손글씨 데이터셋 분류 추론 모델 만들기..

오이띠 2021. 5. 10. 14:37
728x90

신경망의 사용처

  • 모든 머신러닝에 사용될 수 있다.
  • 분류와 회귀를 알아보자
  • 출력층의 활성화 함수에 따라서 목적(사용처)이 달라진다. ( 분류를 할지, 회귀를 할지 )
  • 일반적으로 항등 함수( identity function )을 활용하면 회귀
  • softmax 또는 시그모이드(σ)를 활용하면 분류
    • 시그모이드(σ) : 이진분류
    • 소프트맥스 : 이진, 다중 분류

 

소프트맥스 함수 구현하기

 

  • k : k번째 출력 ( 클래스 번호 ) 0, 1, 2 ....
  • z : 출력층에 있는 뉴런의 WX+b 연산
  • n : 전체 클래스의 개수

 

softmax의 특징

  • 어떠한 실수 배열이 softmax를 지나게 되면 그 배열의 총합이 언제나 1.0이 된다.
  • 총 합이 1.0 이라는 것의 특징 : 확률로써 설명이 가능하다

 

 

소프트맥스 함수 튜닝

  • 소프트맥스 함수는 지수 함수를 사용
  • 따라서 입력값이 약간만 커져도 굉장히 큰 값을 연산해야 한다.
  • 예시
    • e10 만 되어도 20000 정도임
    • e100 0이 40개가 넘는 큰 숫자
    • e1000 무한대를 의미하는 inf

수학적 기교로 튜닝하기

  1. 분자 분모에 C라는 임의의 정수를 곱합니다.
  2. C를 지수 함수 exp 안으로 옮겨서 logC로 만들어 준다.
  3. logC C이라는 새로운 기호로 만들어 준다.

 

 

출력층의 뉴런 수 정하기

  • 출력층의 뉴런 개수는 적절하게 정해줘야 한다.
  • 분류문제에서는 분류하고 싶은 클래스의 개수대로 설정하는 것이 가장 일반적
  • 예시
    • 강아지, 고양이를 분류하는 모델을 만들고 싶어요
      • 클래스의 개수 : 2개
      • sigmoid를 쓰려면 뉴런의 개수가 1개
      • softmax를 쓰려면 뉴런의 개수가 2개
    • 손글씨 데이터 (MNIST)를 분류하는 모델을 만들고 싶어요
      • 클래스의 개수 : 10개 ( 0 ~ 9 까지의 숫자 )
      • 출력층의 뉴런을 10개로 설정해야 한다.
      • 활성화 함수는 softmax만 사용이 가능하다.
  • 시그모이드 함수는 2진 분류에서만 사용이 가능
  • 소프트맥스 함수는 2진 분류, 다중 분류에서도 사용이 가능하다. ( 가장 범용적으로 사용이 된다. )

 

MNIST 손글씨 데이터셋 분류 추론 모델 만들기

  • 학습은 하지 않고, 추론(predict)만 하는 모델을 만들어 보기
  • sample_weight.pkl 파일에 학습이 완료된 가중치와 편향이 들어 있음!

Tensorflow MNIST 데이터 불러오고 형상 다루기

 

 

데이터 확인하기

  • 이미지 데이터는 이미지를 표시하는 것

데이터를 신경망에 집어 넣을 준비 - 훈련과 학습, 테스트 모두 동일한 shape을 가져야 한다. 각 데이터를 모두 1차원 형식으로 집어넣어야 한다.

하나의 데이터를 1차원 배열( 벡터 )로 받는 신경망

  • 신경망 - Dense Layer ( 신경망 기술적인 표현으로 이야기 할 때 )
  • 기하학 - Affine Transformation ( Affine Layer )
  • 종합적 - Fully Connected Layer - 완전 연결 계층이란 표현으로 많이 사용

신경망에 1장의 이미지 데이터를 입력할 수 있는 경우 확인하기 - shape을 확인하기

  • 몇 장인지에 대한 정보 없이 세로 픽셀, 가로 픽셀만 있는 상황 : (28, 28) -> X
  • 몇 장인지에 대한 정보 없이 이미지 정보를 평탄화 한 상황 : (784, ) -> O

신경망에 N장의 이미지 데이터를 입력할 수 있는 경우 확인하기

  • 몇 장인지에 대한 정보가 존재하는 형태로 세로 픽셀, 가로 픽셀의 정보가 있는 상황 : (N, 28, 28) -> X
  • 몇 장인지에 대한 정보가 존재하는 형태로 이미지 정보를 평탄화 한 상황 : (N, 784) -> O

결론적으로 입력되는 데이터의 차원이 (N, M) 이면 신경망( F.C 레이어 )에 집어 넣을 수 있다.

  • N : 데이터의 개수 ( N장의 이미지 )
  • M : 데이터의 스칼라의 개수
    • 데이터의 개수를 이야기를 안 하면 (1개의 데이터에 대한 이야기) : (M, ) 또는 (1, M)
    • 데이터의 개수를 이야기 하면 ( N개의 데이터에 대한 이야기 ) : (N, M)

참고로 CNN은 Fully Conneected Layer가 아니고, 특징 추출( Feature Extraction )이라는 과정으로써, 단순한 2차원 데이터가 아닌, (N, H, W, C)가 입력 데이터의 모양이 됩니다.

 

 

신경망에 들어가는 형태로 이미지 배열 편집하기

 

 

 

MNIST 신경망 만들기 - F.C.L

 

  • pred_image는 7의 모양을 한 이미지
  • y_test[0]은 pred_image의 정답. 7
  • pred_result는 pred_image의 softmax 결과물
  • np.argmax(pred_result)를 이용하여 가장 확률이 높은 인덱스를 확인해 보니 7
  • 즉 예측이 잘 됐다.

 

 

배치 (BATCH)

배치란 데이터의 묶음

  • 일반 배치
    • 데이터를 순서대로 묶은 것
    • 데이터가 모자라거나 적당하게 모아낸 경우
  • 미니 배치
    • 데이터를 랜덤하게 뽑아서 묶은 것
    • 빅 데이터 같은 데이터의 양(Data Volume)이 엄청나게 큰 경우
    • 엄청나게 많은 데이터를 모두 사용해서 훈련을 한다면 시간이 매우 많이 걸림
    • 랜덤하게 몇 개의 데이터를 선정해서 훈련

 

위 코드의 단점

  • 10,000장의 이미지를 한장씩 예측을 하고 있다.
  • 시간이 오래걸린다는 이야기

어떻게 해결할 수 있을까?

  • 배치(BATCH)를 사용해서 한장씩이 아닌, 데이터의 묶음으로 예측을 하게 하겠다.
  • 배치란? 데이터의 뭉터기

np.argmax의 axis가 1인 이유

  1. softmax의 결과는 10개의 원소(결과물)를 가진 1차원 배열
  2. 그런데, 이 결과물이 100개씩 묶음 지어져 있다.(왜? 배치 때문에... 100장씩 넣었으니까 100개씩 10개의 결과물이 있는 것)
  3. 따라서 np.argmax의 axis를 스칼라가 추가되는 방향인 1로 줘야지만 각 이미지별 최댓값의 인덱스를 구할 수 있다.
  4. axis=0은 1차원 배열이 추가되는 이미지 장수에 대한 방향이기 때문에...
728x90