brunch

You can make anything
by writing

C.S.Lewis

by 라인하트 Jan 09. 2021

머신러닝 옥타브 실습(4-2):신경망손글씨 인식

 온라인 강의 플랫폼 코세라의 창립자인 앤드류 응 (Andrew Ng) 교수는 인공지능 업계의 거장입니다. 그가 스탠퍼드 대학에서 머신 러닝 입문자에게 한 강의를 그대로 코세라 온라인 강의 (Coursera.org)에서 무료로 배울 수 있습니다. 이 강의는 머신러닝 입문자들의 필수코스입니다. 인공지능과 머신러닝을 혼자 공부하면서 자연스럽게 만나게 되는 강의입니다. 



Programming Exercise 4: Neural Networks Learning

프로그래밍 실습 4 : 신경망 학습   


1. Neural Networks (신경망)


1.4 Regularized cost function (정규화된 비용 함수)


The cost function for neural networks with regularization is given by



   You can assume that the neural network will only have 3 layers – an input layer, a hidden layer and an output layer. However, your code should work for any number of input units, hidden units and outputs units. While we have explicitly listed the indices above for Θ(1) and Θ(2) for clarity, do note that your code should in general work with Θ(1) and Θ(2) of any size.

   Note that you should not be regularizing the terms that correspond to the bias. For the matrices Theta1 and Theta2, this corresponds to the first column of each matrix. You should now add regularization to your cost function. Notice that you can first compute the unregularized cost function J using your existing nnCostFunction.m and then later add the cost for the regularization terms.

   Once you are done, ex4.m will call your nnCostFunction using the loaded set of parameters for Theta1 and Theta2, and λ = 1. You should see that the cost is about 0.383770.

   You should now submit your solutions.


   정규화된 신경망의 비용 함수는 다음과 같습니다.  신경망은 입력층, 은닉층, 출력층의 3개 계층만 있습니다. 코드는 모든 입력 유닛, 은닉 유닛, 출력 유닛에서 동작해야 합니다.  Θ^(1)과  Θ^(2)의 차원을 직접 나열하였지만, Θ^(1)과 Θ^(2)는 모든 차원의 크기에서 동작합니다. 

   바이어스 항은 정규화하지 않습니다. 행렬 Theta1과 Theta2는 각 행렬의 첫 번째 열입니다. 비용 함수에 정규화 항을 추가합니다. 먼저 nnCostFunction.m 파일에 비정규화된 작성된 비용 함수 J(Θ)에 대한 코드를 작성하고 정규화 항을 추가합니다.

   완료한 후 ex4.m 파일은 파라미터 Theta1과 Theta2와 함께 nnCostFunction.m을 호출하고 정규화 파라미터 λ = 1입니다. 비용은 약 0.383770입니다. 

   완료 후 설루션을 제출합니다.


<해설>

(1) 데이터 업로드 및 기본 변수 설정 


clear; close all; clc         

load ('ex4data1.mat');  % 5000X 400의 손글씨 숫자 흑백 이미지 행렬을 업로드   

[m, n] = size(X);              % 행렬 X가 5000X 400차원일 때 m = 5000, n= 400    


(2) 신경망 변수 설정


input_layer_size  = 400;    % 20x20 이미지를 입력하기 위한 유닛 수

hidden_layer_size = 25;     % 25 은닉 유닛의 수 

num_labels = 10;                   % 멀티 클래스의 수, 0은 10으로 처리


load('ex4weights.mat');   

nn_params = [Theta1(:) ; Theta2(:)];   % Theta1과 Theta2를 벡터로 변환하고 합침 

lambda = 1;                          % 정규화 파라미터 λ를 초기화                        


(3) nnCostFunction.m 파일 분석


   지난 실습에서 파일을 분석하였습니다. 분석 내용과 결과 값을 정리합니다.


function [J grad] = nnCostFunction(nn_params,input_layer_size, ...

                                   hidden_layer_size, num_labels, X, y, lambda)

%NNCOSTFUNCTION  2층 신경망의 비용 함수 구현 

%

%   [J grad] = NNCOSTFUNCTON(nn_params, hidden_layer_size, num_labels, ...

%   X, y, lambda) 신경망의 비용 J과 기울기 grad를 계산 

%   신경망의 파라미터는 벡터 nn_params로 변환했다가 가중치 행렬로 다시 변환

%

%   변환될 파라미터는 신경망의 편미분에 대한 unrolled 벡터가 변환

%   

%   Reshape() 함수로 nn_params를 Theta1과 Theta2로 전환 

Theta1 = reshape(nn_params(1:hidden_layer_size * (input_layer_size + 1)), ...

                 hidden_layer_size, (input_layer_size + 1));


Theta2 = reshape(nn_params((1 + (hidden_layer_size * (input_layer_size + 1))):end), ...

                 num_labels, (hidden_layer_size + 1));


% 변수 초기화 

m = size(X, 1);

         

% 반환할 변수 초기화  

J = 0;

Theta1_grad = zeros(size(Theta1));

Theta2_grad = zeros(size(Theta2));


% ====================== YOUR CODE HERE ======================

% Instructions: 다음 두 부분을 코드로 완성 

%

% Part 1: 신경망을 피드 포워드 하고 변수 J에 비용을 반환

 %             Part 1을 구현한 후 비용 함수 계산이 맞는 지를 확인

%

% Part 2: 경사를 계산하기 위해 역전파 알고리즘을 구현

%               (Theta1_grad과 Theta2_grad 에 있는 Theta1과 Theta2의 비용 함수의 편미분을 반환

%              Part 2를 구현 후 checkNNGradients를 실행하여 맞는 지를 확인

%

%         노트:  벡터 y는 1부터 K까지를 포함하는 벡터

%               신경망의 비용 함수에 사용되는 1 또는 0으로 된 이진 벡터 

%

%         힌트: 학습 예제를 대상으로 For 루프를 사용하여 역전파를 구현 

%          

%

% Part 3: 비용 함수와 기울기에 대해 정규화를 구현

%

%         힌트: 역전파 코드를 활용하여 정규화된 비용 함수와 기울기 구현 

%                  정규화를 위한 경사를 계산하고 Part 2의 Theta1_grad와 Theta2_grad를 추가

%        

%


X = [ones(m,1) X];

a2 = sigmoid(X*Theta1'); 


a2 = [ones(size(a2,1), 1) a2];

a3 = sigmoid(a2*Theta2'); 


for k = 1:m

    yVec(k,y(k)) = 1;

end 


% Computing Cost Function J

J = - 1/m *sum(sum(yVec .*log(a3) + (1-yVec) .*log(1-a3)));


% -------------------------------------------------------------


% =========================================================================


% 기울기를 언롤링(Unroll)

grad = [Theta1_grad(:) ; Theta2_grad(:)];



end


(4) 정규화된 비용 함수의 이해


   신경망의 정규화된 비용 함수는 다음과 같습니다.


    



(5) 정규화 항 코드 만들기


   마지막 비용 함수에 정규화 항을 추가하기 위해 정규화 항을 계산합니다.


regularizer = lambda/(2*m) * (sum(sum(Theta1(:, 2:end) .* Theta1(:, 2:end))) + sum(sum( Theta2(:, 2:end) .* Theta2(:, 2:end))))


    Theta1(:, 2:end)는  25 X 401차원 행렬 Theta1에서 바이어스 항을 제외한 25 X 400 행렬로 재배열합니다. Theta1(:, 2:end) 행렬 성분을 제곱합니다. Theta2(:, 2:end)는 10 X 26차원 행렬 Theta2에서 바이어스 항을 제외한 10 X 25 행렬로 재배열합니다. Theta2(:, 2:end) 행렬 성분을 제곱합니다.   


   정규화된 비용 함수는 다음과 같습니다. 


   J = - 1/m *sum(sum  (yVec .*log(a3) + (1-yVec) .*log(1-a3)));


   J = J + regularizer;



(6) 결과 확인하기


lambda = 1;


J = nnCostFunction(nn_params, input_layer_size, hidden_layer_size, ...

                   num_labels, X, y, lambda)


J =  0.38377




<정답>


function [J grad] = nnCostFunction(nn_params,input_layer_size, ...

                                   hidden_layer_size, num_labels, X, y, lambda)

%NNCOSTFUNCTION  2층 신경망의 비용 함수 구현 

%

%   [J grad] = NNCOSTFUNCTON(nn_params, hidden_layer_size, num_labels, ...

%   X, y, lambda) 신경망의 비용 J과 기울기 grad를 계산 

%   신경망의 파라미터는 벡터 nn_params로 변환했다가 가중치 행렬로 다시 변환

%

%   변환될 파라미터는 신경망의 편미분에 대한 unrolled 벡터가 변환

%   

%   Reshape() 함수로 nn_params를 Theta1과 Theta2로 전환 

Theta1 = reshape(nn_params(1:hidden_layer_size * (input_layer_size + 1)), ...

                 hidden_layer_size, (input_layer_size + 1));


Theta2 = reshape(nn_params((1 + (hidden_layer_size * (input_layer_size + 1))):end), ...

                 num_labels, (hidden_layer_size + 1));


% 변수 초기화 

m = size(X, 1);

         

% 반환할 변수 초기화  

J = 0;

Theta1_grad = zeros(size(Theta1));

Theta2_grad = zeros(size(Theta2));


% ====================== YOUR CODE HERE ======================

% Instructions: 다음 두 부분을 코드로 완성 

%

% Part 1: 신경망을 피드 포워드 하고 변수 J에 비용을 반환

 %             Part 1을 구현한 후 비용 함수 계산이 맞는 지를 확인

%

% Part 2: 경사를 계산하기 위해 역전파 알고리즘을 구현

%               (Theta1_grad과 Theta2_grad에 있는 Theta1과 Theta2의 비용 함수의 편미분을 반환

%              Part 2를 구현 후 checkNNGradients를 실행하여 맞는 지를 확인

%

%         노트:  벡터 y는 1부터 K까지를 포함하는 벡터

%               신경망의 비용 함수에 사용되는 1 또는 0으로 된 이진 벡터 

%

%         힌트: 학습 예제를 대상으로 For 루프를 사용하여 역전파를 구현 

%          

%

% Part 3: 비용 함수와 기울기에 대해 정규화를 구현

%

%         힌트: 역전파 코드를 활용하여 정규화된 비용 함수와 기울기 구현 

%                  정규화를 위한 경사를 계산하고 Part 2의 Theta1_grad와 Theta2_grad를 추가

%        

%


X = [ones(m,1) X];

a2 = sigmoid(X*Theta1');

 

a2 = [ones(size(a2,1), 1) a2];

a3 = sigmoid(a2*Theta2'); 


for k = 1:m

    yVec(k,y(k)) = 1;

end 


% Computing Cost Function J

J = - 1/m *sum(sum(yVec .*log(a3) + (1-yVec) .*log(1-a3))); 


% Computing Regularized Cost Function J

regularizer = lambda/(2*m) * (sum(sum(Theta1(:, 2:end) .^2 )) + sum(sum (Theta2(:, 2:end) .^2))) ;


J = J + regularizer;


% -------------------------------------------------------------


% =========================================================================


% 기울기를 언롤링(Unroll)

grad = [Theta1_grad(:) ; Theta2_grad(:)];



end



< 결과 확인 >


clear; close all; clc         

load ('ex4data1.mat');    

[m, n] = size(X);              


input_layer_size  = 400;    

hidden_layer_size = 25;     

num_labels = 10;                 


load('ex4weights.mat');   

nn_params = [Theta1(:) ; Theta2(:)];     

lambda = 1;


>> J = nnCostFunction(nn_params, input_layer_size, hidden_layer_size, ...

                   num_labels, X, y, lambda)


J =  0.38377


비용은 약 0.383770입니다. 




매거진의 이전글 머신러닝 옥타브 실습(4-1):신경망손글씨 인식
작품 선택
키워드 선택 0 / 3 0
댓글여부
afliean
브런치는 최신 브라우저에 최적화 되어있습니다. IE chrome safari