{
  "cells": [
    {
      "cell_type": "code",
      "execution_count": null,
      "metadata": {
        "id": "DA42OJmJ1PUv"
      },
      "outputs": [],
      "source": [
        "import pandas as pd\n",
        "import numpy as np\n",
        "import matplotlib.pyplot as plt\n",
        "import sys"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": null,
      "metadata": {
        "id": "_xMpZeS71PUz"
      },
      "outputs": [],
      "source": [
        "\n",
        "def sigmoid(z):\n",
        "  return 1.0/(1 + np.exp(-z))\n",
        "\n",
        "def onehot(y, n_classes):\n",
        "  # Encode labels into one-hot representation\n",
        "  # y: labels [n_samples]\n",
        "  # n_classes: number of classes\n",
        "  # return onehot: [n_samples, n_classlabels]\n",
        "\n",
        "  n_samples = y.shape[0]\n",
        "  y_onehot = np.zeros((n_samples, n_classes))\n",
        "  for i in range(y.shape[0]):\n",
        "    y_onehot[i, y[i]] = 1\n",
        "\n",
        "  return y_onehot\n",
        "\n",
        "def forward(X, w_h, b_h, w_out, b_out):\n",
        "  # step 1: net input of hidden layer, z_h [n_samples, n_hidden]\n",
        "  # step 2: activation of hidden layer, a_h [n_samples, n_hidden]\n",
        "  # step 3: net input of output layer, z_out [n_samples, n_classlabels]\n",
        "  # step 4: activation output layer, a_out [n_samples, n_classlabels]\n",
        "\n",
        "  z_h = np.matmul(X, w_h) + b_h\n",
        "  a_h = sigmoid(z_h)\n",
        "  z_out = np.matmul(a_h, w_out) + b_out\n",
        "  a_out = sigmoid(z_out)\n",
        "  return z_h, a_h, z_out, a_out\n",
        "\n",
        "def compute_cost(y_onehot, output, l2, w_h, w_out):\n",
        "  # Compute cost function\n",
        "  # y_onehot: one-hot encoded output [n_samples, n_classlabels]\n",
        "  # output: activation output, a_out [n_samples, n_classlabels]\n",
        "  # l2: regularization coefficient lambda\n",
        "  # w_h, w_out: current weight for hidden and output layers\n",
        "  # return cost: cost value with l2 reguralization\n",
        "\n",
        "  m = y_onehot.shape[0]\n",
        "\n",
        "  cost1 = - np.sum(y_onehot * np.log(output) + (1.-y_onehot) * np.log(1.0-output))\n",
        "  l2_term = np.sum(w_h**2.) + np.sum(w_out**2.)\n",
        "  cost = cost1 + l2*l2_term\n",
        "\n",
        "  return cost\n",
        "\n",
        "def predict(X, w_h, b_h, w_out, b_out):\n",
        "  # predict class labels\n",
        "  # X: input array [n_samples, n_features]\n",
        "  # y_pred: prediced class labels [n_samples]\n",
        "\n",
        "  _, _, _, a_out = forward(X, w_h, b_h, w_out, b_out)\n",
        "  y_pred = np.argmax(a_out, axis=1)\n",
        "\n",
        "  return y_pred\n",
        "\n",
        "def train(X_train, Y_train, X_valid, Y_valid, n_hidden=30, eta=0.0001, n_iter=100, minibatch_size=1, l2=0):\n",
        "  # Learn weights from training data\n",
        "  # X_train: input array [n_samples, n_features]\n",
        "  # Y_train: target class labels [n_samples]\n",
        "  # n_hidden: number of units in hidden layer\n",
        "  # eta: learning rate\n",
        "  # n_iter: max number of iterations\n",
        "  # minibatch_size: number of minibatch\n",
        "  # l2: regularization coefficient lambda\n",
        "  # return learned weights\n",
        "\n",
        "  # 1. Initialize the wegiths\n",
        "\n",
        "  n_classes = np.max(Y_train)+1\n",
        "  n_feature = X_train.shape[1]\n",
        "\n",
        "  b_h = np.zeros(n_hidden)\n",
        "  b_out = np.zeros(n_classes)\n",
        "  w_h = np.random.randn(n_feature, n_hidden)\n",
        "  w_out = np.random.randn(n_hidden, n_classes)\n",
        "  cost_best = 1e+8\n",
        "  w_h_best = np.random.randn(n_feature, n_hidden)\n",
        "  w_out_best = np.random.randn(n_hidden, n_classes)\n",
        "  b_h_best = np.zeros(n_hidden)\n",
        "  b_out_best = np.zeros(n_classes)\n",
        "\n",
        "  # 2. One-hot encoding of Y_train\n",
        "  y_onehot = onehot(Y_train, n_classes)\n",
        "  y_valid_onehot = onehot(Y_valid, n_classes)\n",
        "\n",
        "  # 3. Do iterations\n",
        "  for i in range(n_iter):\n",
        "\n",
        "    idx = np.arange(X_train.shape[0])\n",
        "\n",
        "    # 4. Do iterations for minibatch\n",
        "    for start_idx in range(0, X_train.shape[0]-minibatch_size+1, minibatch_size):\n",
        "\n",
        "      batch_idx = idx[start_idx:start_idx+minibatch_size]\n",
        "      X_train_batch = X_train[batch_idx]\n",
        "\n",
        "      # 5. Forward X_train_batch\n",
        "      z_h, a_h, z_out, a_out = forward(X_train_batch, w_h, b_h, w_out, b_out)\n",
        "\n",
        "      # 6. Set delta_out and grad_w_out, grad_b_out\n",
        "      delta_out = a_out - y_onehot[batch_idx]\n",
        "      grad_w_out = np.matmul(a_h.T, delta_out) + l2*w_out\n",
        "      grad_b_out = np.sum(delta_out, axis=0)\n",
        "\n",
        "      # 7. Set delta_h and grad_w_h, grad_b_h\n",
        "      delta_h = np.matmul(delta_out, w_out.T) * (a_h * (1. -a_h))\n",
        "      grad_w_h = np.dot(X_train[batch_idx].T, delta_h)\n",
        "      grad_b_h = np.sum(delta_h, axis=0)\n",
        "\n",
        "\n",
        "      # 8. Update weights: w_h, b_h, w_out, b_out\n",
        "      b_h -= eta*grad_b_h\n",
        "      w_h -= eta*grad_w_h\n",
        "      b_out -= eta*grad_b_out\n",
        "      w_out -= eta*grad_w_out\n",
        "\n",
        "\n",
        "    # 9. Get a_out\n",
        "    _, _, _, a_out = forward(X_train, w_h, b_h, w_out, b_out)\n",
        "    _, _, _, a_out_val = forward(X_valid, w_h, b_h, w_out, b_out)\n",
        "\n",
        "    # 10. Compute cost\n",
        "    cost = compute_cost(y_onehot, a_out, l2, w_h, w_out)\n",
        "\n",
        "\n",
        "    # 11. Predict y_train_pred\n",
        "    y_train_pred = predict(X_train, w_h, b_h, w_out, b_out)\n",
        "    y_valid_pred = predict(X_valid, w_h, b_h, w_out, b_out)\n",
        "\n",
        "    # 12. Check the training results\n",
        "    train_acc = ((np.sum(Y_train == y_train_pred)).astype(float) / X_train.shape[0])\n",
        "\n",
        "    # 13. Check the validation results: validation accuracy(valid_acc) and validation cost(valid_cost)\n",
        "    ## initialize cost_best\n",
        "    valid_cost = compute_cost(y_valid_onehot, a_out_val, l2, w_h, w_out)\n",
        "    valid_acc = ((np.sum(Y_valid == y_valid_pred)).astype(float) / X_valid.shape[0])\n",
        "\n",
        "\n",
        "\n",
        "    # 14. Update the weight if the current cost is smaller than the saved one\n",
        "    if cost_best>valid_cost:\n",
        "      b_h_best = b_h\n",
        "      w_h_best = w_h\n",
        "      cost_best = valid_cost\n",
        "      b_out_best = b_out\n",
        "      w_out_best = w_out\n",
        "      print(i)\n",
        "\n",
        "\n",
        "    sys.stderr.write('%d/%d | Train Cost: %.2f | Acc.: %.2f%% ' %(i+1, n_iter, cost, train_acc*100))\n",
        "    sys.stderr.write('| Validation Cost: %.2f | Acc.: %.2f%% \\n' %(valid_cost, valid_acc*100))\n",
        "    sys.stderr.flush()\n",
        "\n",
        "  return w_h_best, b_h_best, w_out_best, b_out_best\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": null,
      "metadata": {
        "colab": {
          "base_uri": "https://localhost:8080/",
          "height": 237
        },
        "id": "9UpXaLX91PUz",
        "outputId": "093b3176-ac45-4b29-f33f-d31cba88d223"
      },
      "outputs": [
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "[[0. 0. 0. 0. 0. 1. 0. 0. 0. 0.]\n",
            " [0. 0. 0. 0. 0. 0. 0. 1. 0. 0.]\n",
            " [0. 0. 0. 0. 0. 0. 0. 0. 0. 1.]\n",
            " [0. 0. 0. 0. 0. 1. 0. 0. 0. 0.]\n",
            " [0. 0. 1. 0. 0. 0. 0. 0. 0. 0.]]\n"
          ]
        },
        {
          "output_type": "display_data",
          "data": {
            "text/plain": [
              "<Figure size 640x480 with 5 Axes>"
            ],
            "image/png": "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\n"
          },
          "metadata": {}
        }
      ],
      "source": [
        "# load the training data\n",
        "data = pd.read_csv('/content/sample_data/mnist_train_small.csv')\n",
        "data = np.array(data)\n",
        "Y_train = data[:7000,0]\n",
        "X_train = data[:7000,1:]/255\n",
        "Y_valid = data[7000:,0]\n",
        "X_valid = data[7000:,1:]/255\n",
        "print(onehot(Y_train, 10)[0:5,:])\n",
        "\n",
        "# Visualize the input data\n",
        "fig, ax = plt.subplots(nrows=1, ncols=5, sharex=True, sharey=True)\n",
        "ax = ax.flatten()\n",
        "for i in range(5):\n",
        "  img = X_train[i,:].reshape(28,28)\n",
        "  ax[i].imshow(img,cmap='Greys',)\n",
        "ax[0].set_xticks([])\n",
        "ax[0].set_yticks([])\n",
        "plt.tight_layout()"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": null,
      "metadata": {
        "colab": {
          "base_uri": "https://localhost:8080/"
        },
        "id": "-lxUAyS81PU0",
        "outputId": "ce2c208d-d477-4993-d53a-4dc7bdd1ba05"
      },
      "outputs": [
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "1/100 | Train Cost: 228971.11 | Acc.: 35.30% | Validation Cost: 412253.67 | Acc.: 34.86% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "0\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "2/100 | Train Cost: 44698.47 | Acc.: 67.00% | Validation Cost: 68973.34 | Acc.: 65.81% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "1\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "3/100 | Train Cost: 34120.93 | Acc.: 77.47% | Validation Cost: 50472.02 | Acc.: 76.62% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "2\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "4/100 | Train Cost: 37710.58 | Acc.: 79.80% | Validation Cost: 55412.55 | Acc.: 79.11% \n",
            "5/100 | Train Cost: 25848.86 | Acc.: 85.94% | Validation Cost: 35601.87 | Acc.: 83.64% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "4\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "6/100 | Train Cost: 29651.42 | Acc.: 82.43% | Validation Cost: 43081.20 | Acc.: 80.79% \n",
            "7/100 | Train Cost: 22507.95 | Acc.: 90.11% | Validation Cost: 29485.71 | Acc.: 87.73% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "6\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "8/100 | Train Cost: 39941.19 | Acc.: 84.76% | Validation Cost: 62607.01 | Acc.: 82.49% \n",
            "9/100 | Train Cost: 21390.37 | Acc.: 92.47% | Validation Cost: 27611.76 | Acc.: 89.73% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "8\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "10/100 | Train Cost: 20267.88 | Acc.: 94.46% | Validation Cost: 25308.93 | Acc.: 91.03% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "9\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "11/100 | Train Cost: 20492.90 | Acc.: 93.86% | Validation Cost: 25911.78 | Acc.: 90.94% \n",
            "12/100 | Train Cost: 33065.64 | Acc.: 85.59% | Validation Cost: 50080.19 | Acc.: 82.79% \n",
            "13/100 | Train Cost: 19847.18 | Acc.: 95.34% | Validation Cost: 24696.00 | Acc.: 91.38% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "12\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "14/100 | Train Cost: 19820.67 | Acc.: 95.47% | Validation Cost: 24798.73 | Acc.: 91.60% \n",
            "15/100 | Train Cost: 19825.16 | Acc.: 95.47% | Validation Cost: 24756.23 | Acc.: 91.71% \n",
            "16/100 | Train Cost: 30510.40 | Acc.: 86.61% | Validation Cost: 45327.46 | Acc.: 83.56% \n",
            "17/100 | Train Cost: 19651.43 | Acc.: 95.93% | Validation Cost: 24523.99 | Acc.: 91.82% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "16\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "18/100 | Train Cost: 20585.78 | Acc.: 94.41% | Validation Cost: 26460.01 | Acc.: 90.71% \n",
            "19/100 | Train Cost: 19581.88 | Acc.: 96.29% | Validation Cost: 24393.41 | Acc.: 92.05% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "18\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "20/100 | Train Cost: 19574.58 | Acc.: 96.36% | Validation Cost: 24407.17 | Acc.: 92.06% \n",
            "21/100 | Train Cost: 19532.74 | Acc.: 96.56% | Validation Cost: 24358.86 | Acc.: 92.15% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "20\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "22/100 | Train Cost: 19488.50 | Acc.: 96.67% | Validation Cost: 24299.74 | Acc.: 92.16% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "21\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "23/100 | Train Cost: 19439.36 | Acc.: 96.77% | Validation Cost: 24215.68 | Acc.: 92.26% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "22\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "24/100 | Train Cost: 19405.60 | Acc.: 96.89% | Validation Cost: 24162.61 | Acc.: 92.37% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "23\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "25/100 | Train Cost: 19375.65 | Acc.: 97.03% | Validation Cost: 24106.37 | Acc.: 92.32% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "24\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "26/100 | Train Cost: 19350.09 | Acc.: 97.10% | Validation Cost: 24067.84 | Acc.: 92.35% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "25\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "27/100 | Train Cost: 19324.32 | Acc.: 97.23% | Validation Cost: 24035.44 | Acc.: 92.35% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "26\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "28/100 | Train Cost: 19299.06 | Acc.: 97.29% | Validation Cost: 24015.26 | Acc.: 92.33% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "27\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "29/100 | Train Cost: 19275.59 | Acc.: 97.37% | Validation Cost: 23992.40 | Acc.: 92.37% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "28\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "30/100 | Train Cost: 19252.57 | Acc.: 97.36% | Validation Cost: 23969.15 | Acc.: 92.41% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "29\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "31/100 | Train Cost: 19231.18 | Acc.: 97.41% | Validation Cost: 23945.77 | Acc.: 92.41% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "30\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "32/100 | Train Cost: 19212.11 | Acc.: 97.44% | Validation Cost: 23923.75 | Acc.: 92.46% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "31\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "33/100 | Train Cost: 19195.08 | Acc.: 97.50% | Validation Cost: 23902.44 | Acc.: 92.55% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "32\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "34/100 | Train Cost: 19179.05 | Acc.: 97.56% | Validation Cost: 23882.66 | Acc.: 92.59% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "33\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "35/100 | Train Cost: 19162.35 | Acc.: 97.63% | Validation Cost: 23861.58 | Acc.: 92.59% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "34\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "36/100 | Train Cost: 19147.18 | Acc.: 97.66% | Validation Cost: 23841.78 | Acc.: 92.62% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "35\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "37/100 | Train Cost: 19132.85 | Acc.: 97.69% | Validation Cost: 23822.49 | Acc.: 92.62% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "36\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "38/100 | Train Cost: 19119.67 | Acc.: 97.71% | Validation Cost: 23804.97 | Acc.: 92.65% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "37\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "39/100 | Train Cost: 19107.61 | Acc.: 97.76% | Validation Cost: 23789.31 | Acc.: 92.70% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "38\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "40/100 | Train Cost: 19096.27 | Acc.: 97.81% | Validation Cost: 23775.35 | Acc.: 92.70% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "39\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "41/100 | Train Cost: 19084.72 | Acc.: 97.83% | Validation Cost: 23761.78 | Acc.: 92.72% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "40\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "42/100 | Train Cost: 19073.08 | Acc.: 97.91% | Validation Cost: 23748.28 | Acc.: 92.74% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "41\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "43/100 | Train Cost: 19062.15 | Acc.: 97.97% | Validation Cost: 23736.29 | Acc.: 92.78% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "42\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "44/100 | Train Cost: 19052.27 | Acc.: 98.03% | Validation Cost: 23726.03 | Acc.: 92.79% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "43\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "45/100 | Train Cost: 19041.48 | Acc.: 98.03% | Validation Cost: 23715.40 | Acc.: 92.79% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "44\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "46/100 | Train Cost: 19029.65 | Acc.: 98.04% | Validation Cost: 23704.79 | Acc.: 92.78% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "45\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "47/100 | Train Cost: 19019.33 | Acc.: 98.13% | Validation Cost: 23695.17 | Acc.: 92.85% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "46\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "48/100 | Train Cost: 19009.52 | Acc.: 98.19% | Validation Cost: 23684.14 | Acc.: 92.85% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "47\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "49/100 | Train Cost: 18999.69 | Acc.: 98.19% | Validation Cost: 23671.95 | Acc.: 92.82% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "48\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "50/100 | Train Cost: 18989.97 | Acc.: 98.23% | Validation Cost: 23660.02 | Acc.: 92.81% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "49\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "51/100 | Train Cost: 18980.50 | Acc.: 98.23% | Validation Cost: 23649.10 | Acc.: 92.84% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "50\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "52/100 | Train Cost: 18971.64 | Acc.: 98.26% | Validation Cost: 23639.10 | Acc.: 92.84% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "51\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "53/100 | Train Cost: 18963.37 | Acc.: 98.26% | Validation Cost: 23629.78 | Acc.: 92.88% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "52\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "54/100 | Train Cost: 18955.56 | Acc.: 98.27% | Validation Cost: 23621.09 | Acc.: 92.91% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "53\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "55/100 | Train Cost: 18948.24 | Acc.: 98.29% | Validation Cost: 23612.51 | Acc.: 92.94% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "54\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "56/100 | Train Cost: 18941.59 | Acc.: 98.31% | Validation Cost: 23604.09 | Acc.: 92.97% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "55\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "57/100 | Train Cost: 18935.43 | Acc.: 98.31% | Validation Cost: 23597.18 | Acc.: 92.98% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "56\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "58/100 | Train Cost: 18929.71 | Acc.: 98.33% | Validation Cost: 23591.01 | Acc.: 93.01% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "57\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "59/100 | Train Cost: 18924.53 | Acc.: 98.33% | Validation Cost: 23585.04 | Acc.: 93.05% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "58\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "60/100 | Train Cost: 18919.65 | Acc.: 98.34% | Validation Cost: 23579.24 | Acc.: 93.07% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "59\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "61/100 | Train Cost: 18915.13 | Acc.: 98.37% | Validation Cost: 23573.96 | Acc.: 93.09% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "60\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "62/100 | Train Cost: 18910.96 | Acc.: 98.37% | Validation Cost: 23569.30 | Acc.: 93.10% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "61\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "63/100 | Train Cost: 18907.01 | Acc.: 98.37% | Validation Cost: 23565.15 | Acc.: 93.11% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "62\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "64/100 | Train Cost: 18903.06 | Acc.: 98.40% | Validation Cost: 23561.32 | Acc.: 93.11% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "63\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "65/100 | Train Cost: 18898.93 | Acc.: 98.41% | Validation Cost: 23557.62 | Acc.: 93.09% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "64\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "66/100 | Train Cost: 18894.68 | Acc.: 98.46% | Validation Cost: 23554.03 | Acc.: 93.10% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "65\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "67/100 | Train Cost: 18890.55 | Acc.: 98.46% | Validation Cost: 23550.52 | Acc.: 93.11% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "66\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "68/100 | Train Cost: 18886.66 | Acc.: 98.49% | Validation Cost: 23547.08 | Acc.: 93.09% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "67\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "69/100 | Train Cost: 18883.02 | Acc.: 98.50% | Validation Cost: 23543.91 | Acc.: 93.14% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "68\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "70/100 | Train Cost: 18879.59 | Acc.: 98.51% | Validation Cost: 23541.22 | Acc.: 93.15% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "69\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "71/100 | Train Cost: 18876.33 | Acc.: 98.53% | Validation Cost: 23538.90 | Acc.: 93.15% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "70\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "72/100 | Train Cost: 18873.19 | Acc.: 98.53% | Validation Cost: 23536.76 | Acc.: 93.15% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "71\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "73/100 | Train Cost: 18870.10 | Acc.: 98.53% | Validation Cost: 23534.64 | Acc.: 93.17% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "72\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "74/100 | Train Cost: 18867.00 | Acc.: 98.53% | Validation Cost: 23532.47 | Acc.: 93.17% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "73\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "75/100 | Train Cost: 18863.84 | Acc.: 98.53% | Validation Cost: 23530.17 | Acc.: 93.15% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "74\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "76/100 | Train Cost: 18860.60 | Acc.: 98.54% | Validation Cost: 23527.73 | Acc.: 93.16% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "75\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "77/100 | Train Cost: 18857.29 | Acc.: 98.57% | Validation Cost: 23525.14 | Acc.: 93.15% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "76\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "78/100 | Train Cost: 18853.95 | Acc.: 98.57% | Validation Cost: 23522.51 | Acc.: 93.15% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "77\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "79/100 | Train Cost: 18850.65 | Acc.: 98.59% | Validation Cost: 23520.01 | Acc.: 93.18% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "78\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "80/100 | Train Cost: 18847.48 | Acc.: 98.59% | Validation Cost: 23517.77 | Acc.: 93.21% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "79\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "81/100 | Train Cost: 18844.51 | Acc.: 98.59% | Validation Cost: 23515.79 | Acc.: 93.21% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "80\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "82/100 | Train Cost: 18841.81 | Acc.: 98.59% | Validation Cost: 23513.91 | Acc.: 93.20% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "81\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "83/100 | Train Cost: 18839.34 | Acc.: 98.57% | Validation Cost: 23511.91 | Acc.: 93.21% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "82\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "84/100 | Train Cost: 18837.02 | Acc.: 98.57% | Validation Cost: 23509.69 | Acc.: 93.20% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "83\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "85/100 | Train Cost: 18834.76 | Acc.: 98.57% | Validation Cost: 23507.27 | Acc.: 93.19% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "84\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "86/100 | Train Cost: 18832.51 | Acc.: 98.59% | Validation Cost: 23504.76 | Acc.: 93.19% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "85\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "87/100 | Train Cost: 18830.36 | Acc.: 98.60% | Validation Cost: 23502.46 | Acc.: 93.21% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "86\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "88/100 | Train Cost: 18828.49 | Acc.: 98.63% | Validation Cost: 23500.73 | Acc.: 93.19% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "87\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "89/100 | Train Cost: 18826.90 | Acc.: 98.63% | Validation Cost: 23499.49 | Acc.: 93.20% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "88\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "90/100 | Train Cost: 18825.37 | Acc.: 98.63% | Validation Cost: 23498.15 | Acc.: 93.19% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "89\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "91/100 | Train Cost: 18823.80 | Acc.: 98.64% | Validation Cost: 23496.64 | Acc.: 93.18% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "90\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "92/100 | Train Cost: 18822.19 | Acc.: 98.64% | Validation Cost: 23495.10 | Acc.: 93.16% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "91\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "93/100 | Train Cost: 18820.54 | Acc.: 98.66% | Validation Cost: 23493.57 | Acc.: 93.15% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "92\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "94/100 | Train Cost: 18818.86 | Acc.: 98.67% | Validation Cost: 23491.94 | Acc.: 93.17% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "93\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "95/100 | Train Cost: 18817.14 | Acc.: 98.67% | Validation Cost: 23490.09 | Acc.: 93.21% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "94\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "96/100 | Train Cost: 18815.34 | Acc.: 98.67% | Validation Cost: 23487.90 | Acc.: 93.21% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "95\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "97/100 | Train Cost: 18813.46 | Acc.: 98.67% | Validation Cost: 23485.44 | Acc.: 93.21% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "96\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "98/100 | Train Cost: 18811.54 | Acc.: 98.69% | Validation Cost: 23482.89 | Acc.: 93.21% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "97\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "99/100 | Train Cost: 18809.64 | Acc.: 98.70% | Validation Cost: 23480.40 | Acc.: 93.22% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "98\n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stderr",
          "text": [
            "100/100 | Train Cost: 18807.78 | Acc.: 98.73% | Validation Cost: 23478.08 | Acc.: 93.23% \n"
          ]
        },
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "99\n"
          ]
        }
      ],
      "source": [
        "# Train the ANN\n",
        "w_h, b_h, w_out, b_out = train(X_train, Y_train, X_valid, Y_valid, n_hidden=200, eta=0.05, n_iter=100, minibatch_size=200, l2=0.1)\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": null,
      "metadata": {
        "colab": {
          "base_uri": "https://localhost:8080/"
        },
        "id": "T2THY7sf1PU1",
        "outputId": "970f1cf0-8212-4d52-fcf1-494cb9c5dd06"
      },
      "outputs": [
        {
          "output_type": "stream",
          "name": "stdout",
          "text": [
            "Test accuracy: 92.92%\n"
          ]
        }
      ],
      "source": [
        "# load the test data\n",
        "data = pd.read_csv('/content/sample_data/mnist_test.csv')\n",
        "data = np.array(data)\n",
        "Y_test = data[:,0]\n",
        "X_test = data[:,1:]/255\n",
        "\n",
        "y_test_pred = predict(X_test, w_h, b_h, w_out, b_out)\n",
        "acc = (np.sum(Y_test == y_test_pred).astype(float) / X_test.shape[0])\n",
        "print('Test accuracy: %.2f%%' % (acc * 100))\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": null,
      "metadata": {
        "id": "y2HL_a9P_Z-Q"
      },
      "outputs": [],
      "source": []
    }
  ],
  "metadata": {
    "colab": {
      "provenance": []
    },
    "kernelspec": {
      "display_name": "ML4ME",
      "language": "python",
      "name": "python3"
    },
    "language_info": {
      "codemirror_mode": {
        "name": "ipython",
        "version": 3
      },
      "file_extension": ".py",
      "mimetype": "text/x-python",
      "name": "python",
      "nbconvert_exporter": "python",
      "pygments_lexer": "ipython3",
      "version": "3.8.18"
    }
  },
  "nbformat": 4,
  "nbformat_minor": 0
}