밑에 찾아 본 생키가 있어서 혹시 그 사이에 형이 업뎃 했는지 기억이 안나고, 마침 주석 똥글이 흥해서 싸줌.


참고로 전반부 주석은 응센세 과제에 원래 있던거거나 형이랑 생각이 달라서 형이 코드를 커맨트로 막아 버림. 주석 백날 봐봐라 코드를 모르면 주석을 봐도 걍 모르는게 이런 류 코드

(야 근데 이게 왜 원래 숙제 코드와 다른지 알아본건 아직까지 코세 뿐이여 ㅋㅋ)


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

                                   input_layer_size, ...

                                   hidden_layer_size_vector, ...

                                   num_labels, ...

                                   X, y, lambda)


  %% costFnNN Implements the neural network cost function for a two layer

  %% neural network which performs classification

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

  %%   X, y, lambda) computes the cost and gradient of the neural network. The

  %%   parameters for the neural network are "unrolled" into the vector

  %%   nn_params and need to be converted back into the weight matrices. 


  %%   The returned parameter grad should be a "unrolled" vector of the

  %%   partial derivatives of the neural network.


  m = numel(y);

  

  %% 1. Build Thetas

  Thetas = nnThetaCell(nn_params, [input_layer_size hidden_layer_size_vector num_labels]);


  %% 2. Set y_matrix

  y_matrix = eye(num_labels)(y,:); % permutation over identity matrix of size num_labels!


  %% 3. Init configuration

  activationLayers = {[ones(m, 1) X]};

  Zs = {};

  sum_Thetas = 0;

  num_theta = numel(Thetas);

  num_layers = num_theta + 1;


  %% 3. forward propagation

  for thetai = 1:num_theta

    z = activationLayers{thetai} * Thetas{thetai}';

    if num_theta > thetai

      activationLayers{thetai + 1} = [ones(m,1) sigmoid(z)];

    else

      activationLayers{thetai + 1} = sigmoid(z);

    end

    sum_Thetas = sum_Thetas + sum(sum(Thetas{thetai}(:,2:end) .^ 2));

    Zs{thetai + 1} = z;

  end


  %% 4. backpropagation

  error_d = activationLayers{num_layers} - y_matrix;

  Deltas = {};


  for i = num_layers-1:-1:1

    Delta = error_d' * activationLayers{i};

    Deltas{i} = Delta;

    

    if i > 1 % Don't process input layer

      error_d = error_d * Thetas{i}(:, 2:end) .* sigmoidGradient(Zs{i});

    end

  end


  %% 5. compute J

  true_classification = y_matrix .* log(activationLayers{num_layers});

  false_classification = (1 - y_matrix) .* log(1 - activationLayers{num_layers});


  scaled_sum_Thetas = (lambda * sum_Thetas)/ (2 * m);

  J = -1/m * sum(sum(true_classification + false_classification)) + ...

      scaled_sum_Thetas;

  

  %% 6. Compute grad

  grad = [];


  for i = 1:num_theta

    Thetas{i}(:, 1) = 0;

    Theta_grad =  1/m * (Deltas{i} + lambda * Thetas{i});

    grad = [grad; Theta_grad(:)];

  end


end