backpropagation step by step

Contoh Perhitungan Algoritma Backpropagation

Beberapa waktu lalu saya dapat kesempatan untuk mengasisteni kegiatan kemkominfo di UGM seputar AI. Salah satu topik yang dibicarakan adalah Backpropagation pada Jaringan Saraf Tiruan (JST). Di postingan ini saya akan mencontohkan perhitungan Backpropagation langkah per langkah, menggunakan arsitektur yang sederhana dan dilanjutkan implementasi menggunakan Python.

Artikel ini diupdate pada 8 Agustus 2020

Sebelum memulai, sebaiknya kita mengerti terlebih dahulu dasar-dasar untuk:

Jika masih dirasa banyak yang lupa, silakan refresh kembali materi tersebut.

Overview

model / arsitektur JST sederhana

Sebelum kita mulai, kita ingat kembali beberapa poin penting dalam JST pada ilustrasi di atas.

JST yang akan kita buat di atas terdiri dari 1 layer input dan 1 layer output. Layer input biasanya digunakan untuk menerima input berupa fitur suatu data. Sedangkan layer output biasanya merepresentasikan prediksi kelas dari data tersebut.

Contoh, sebuah data $X$ memiliki 3 fitur dan 2 kelas. Maka, layer input JST terdiri dari 3 neuron dan layer output terdiri dari 2 neuron. Diketahui sebuah data termasuk pada kelas ke-“2” dengan detail nilai fitur input adalah sebagai berikut:

Maka dari data tersebut dapat diketahui representasi dalam JST-nya adalah sebagai berikut:

  1. Fitur-fitur pada $X$, dipetakan dengan variabel $x$ sehingga diperoleh $x_1$=1.0, $x_2$=2.0, $x_3$=0.5
  2. Label kelas, diubah bentuknya menjadi one-hot encoding. One-hot encoding adalah vektor yang semua isinya bernilai 0, kecuali pada index kelas yang sesuai. Misalnya, untuk data dengan dua kelas, maka vektor representasinya memiliki panjang 2, di mana tiap elemen direpresentasikan dengan variabel $t$ menunjukkan index label kelas. Variabel $t_1$ bernilai 1 jika data berlabel kelas ke-1 dengan vektor one-hot encodingnya adalah [1, 0]. Sebaliknya, variabel $t_2$ bernilai 1 ketika data berlabel kelas ke-2 dengan vektor one-hot encodingnya adalah [0, 1]. Contoh data di atas diketahui termasuk pada kelas ke-2, maka vektornya adalah [0, 1], dengan nilai tiap elemennya adalah $t_1$=0 dan $t_2$=1.
  3. JST akan menghitung nilai prediksi $y_1$ dan $y_2$ berdasarkan input $X$. Lalu melalui proses pembelajaran, JST berusaha menghasilkan nilai prediksi $y$ yang sama dengan nilai target $t$

Ada dua bagian utama pada JST, yakni forward propagation dan backward propagation. pada forward propagation, JST akan mencoba menghasilkan nilai $y$, sedangkan pada backward propagation, JST akan memperbaiki dirinya (update bobot) sehingga pada forward propagation berikutnya diharap bisa menghasilkan nilai $y$ yang lebih baik atau lebih mendekati label aslinya.

proses forward dan backward pada JST

Forward Propagation

Forward propagation adalah proses perhitungan secara “maju” dari input (disimbolkan $x$) hingga diperoleh output model (disimbolkan $y$). Misal pada ilustrasi di bawah, adalah proses forward propagation dari input $x$ menuju $y$.

Untuk perhitungannya, nilai $y_1$ diperoleh dengan menghitung nilai $z_1$ terlebih dahulu (perhitungan linier).

$$ z_1 = w_{11}x_{1} + w_{21}x_{2} + w_{31}x_{3} + b_1 $$

Setelah diperoleh $z_1$ , output prediksi $y_1$ diperoleh dengan menerapkan fungsi aktivasi terhadap $z_1$.

$$ y_1 = \sigma \left( z_1 \right) $$

Perhitungan untuk semua $y$ secara umum bisa menggunakan rumus:

$$ y_j = \sigma \left( \sum_{i=1}^\text{N} w_{ij}x_i + b_j \right) $$

Rumus di atas, sangat penting untuk dipahami, untuk penjelasannya simbol-simbolnya:

  • Simbol $b_i$ menunjukkan nilai bias. Nilai bias ini mirip dengan nilai bobot hanya saja tidak dikalikan dengan input. Tujuannya agar garis persamaan bisa lebih kompleks (tidak selalu melewati titik origin).
  • Semua nilai bobot $w$ dan bias $b$ awalnya diberikan nilai random, dan diperbarui nilainya dengan proses backprop untuk meningkatkan kualitas model. Jika diperhatikan kita menamai simbol $w_{ij}$ berarti bobot yang menghubungkan neuron input nomor $i$ ke neuron output nomor $j$.
  • N menunjukkan banyak neuron di layer sebelah kiri (layer input).
  • Simbol $\sigma()$ (sigma) adalah simbol dari fungsi aktivasi. Artinya, setelah proses perkalian input $x$ dan bobot $w$ lalu dilakukan penjumlahan semua, langkah selanjutnya adalah mengenai hasil perhitungan tersebut dengan fungsi aktivasi. Ada banyak fungsi aktivasi yang dapat dipilih salah satunya fungsi aktivasi sigmoid yang bentuknya seperti ini:

$$ \sigma(x) = \frac{1}{1 + e^{-x}} $$

Contoh Forward Propagation

Misalkan kita memiliki sebuah input seperti tabel di atas $X = [1, 2, 0.5]$ dengan nilai bobot dan bias di awal adalah sebagai berikut (nilai awal bobot dan bias adalah nilai random, saya susun seperti matrix agar mudah):

$$ \begin{bmatrix}
w_{11} = 0.2 & w_{12} = 0.3 \\
w_{21} = 0.3 & w_{22} = 0.1 \\
w_{31} = 0.3 & w_{32} = 0.2
\end{bmatrix} $$

$$ [b_1=0, b_2 = 0]$$

Pada contoh di atas simbol $w_{ij}$ berarti bobot yang menghubungkan neuron input nomor $i$ ke neuron output nomor $j$. Misalnya $w_{21}$ artinya bobot yang menghubungkan neuron input nomor 2 dengan neuron output nomor 1 (bisa diperhatikan pada ilustrasi sebelumnya).

Langka pertama forward propagation adalah menghitung nilai $z$. Pada contoh ini dapat kita hitung nilai $z_1$ adalah:

$$\begin{eqnarray}
& z_1 & = w_{11}x_{1} + w_{21}x_{2} + w_{31}x_{3} + b_1 \nonumber \\
& & = 0.2 * 1 + 0.3 * 2 + 0.3 * 0.5 + 0 \nonumber \\
& & = 0.95 \nonumber \\
\end{eqnarray}$$

Lalu setelah itu kita hitung nilai $y_1$:

$$\begin{eqnarray}
& y_1 & = \sigma (z_1) \nonumber \\
& & = \sigma (0.95) \nonumber \\
& & = \frac{1}{1 + e^{-0.95}} \nonumber \\
& & = 0.721 \nonumber \\
\end{eqnarray}$$

Dengan cara perhitungan yang sama dengan di atas dapat diperoleh juga nilai $y_2$ adalah $0.645$. Sampai sini, mungkin sebelum lanjut coba berhenti sebentar dan dipahami lagi prosesnya bagaimana bisa mendapatkan semua nilai $y$.

Error

Dari perhitungan sebelumnya diperoleh nilai sebagai berikut:

$$ [y_1=0.721, y_2=0.645] $$

Nilai tersebut adalah nilai prediksi, atau nilai yang dihasilkan oleh model JST kita. Seperti disebutkan sebelumnya setiap data yang masuk memiliki label kelas atau nilai $y$ yang diharapkan, misalnya untuk data $X$ di atas kita ingin model kita seharusnya bernilai berikut (variabel $t$ adalah nilai target label kelas yang sebenarnya):

$$ [t_1=0, t_2=1] $$

Dari sana tampak perbedaan nilai prediksi kita ($y$) dengan nilai target ($t$). Kita bisa menghitung seberapa melenceng prediksi kita menggunakan rumus untuk menghitung error. Salah satunya adalah dengan rumus Mean Square Error (MSE):

$$ error = \frac{1}{n}\sum_{i=1}^n (target_i – prediksi_i)^2$$

rumus tersebut menghitung selisih nilai target dan prediksi, mengkuadratkannya, lalu merata-ratanya (dijumlah lalu dibagi n). Nilai n di sana adalah banyak datanya, pada contoh ini kita menggunakan n=2 karena ada 2 node output.

Sehingga untuk perhitungan kita di atas, dapat dihitung error $E$ yang dihasilkan adalah sebesar:

$$\begin{eqnarray}
& E & = \frac{1}{2} \sum_{i=1}^2 (target_i – prediksi_i)^2 \nonumber \\
& & = \frac{1}{2}((t_1 – y_1)^2+(t_2 – y_2)^2) \nonumber \\
& & = \frac{1}{2}((0 – 0.721)^2+(1 – 0.645)^2) \nonumber \\
& & = 0.322 \nonumber \
\end{eqnarray}$$

Karena tujuan JST adalah untuk menghasikan nilai prediksi $y$ yang semirip mungkin dengan $t$, maka dapat disebut juga tujuan dari JST adalah meminimalkan nilai error $E$.

Backpropagation

Setelah mendapatkan nilai error, kita bisa mulai memperbaiki JST kita dengan backpropagation. Sebenarnya istilah memperbaiki JST ini kurang tepat jika menyebutnya Backpropagation, lebih tepatnya adalah Gradient Descent. Tapi ya di Indonesia lebih umum menyebutnya Backpropagation kadang disingkat Backprop.

Rumus utama untuk memperbaiki suatu bobot $w$ berdasarkan error $E$ adalah:

$$ w_{new} = w_{old} – \alpha \frac{\partial E}{\partial w} $$

Rumus ini juga berlaku untuk memperbaiki nilai bias:

$$ b_{new} = b_{old} – \alpha \frac{\partial E}{\partial b} $$

Simbol $\alpha$ pada rumus di atas adalah learning rate, sebuah konstanta (biasanya antara 0-1) yang menentukan seberapa cepat proses pembelajaran model dilakukan. Di artikel ini kita akan menggunakan nilai $\alpha = 0.5$. Sedangkan simbol $ \frac{\partial E}{\partial w} $ atau dibaca “turunan parsial $E$ terhadap $w$” adalah proses mencari nilai turunan $E$ terhadap variabel yang akan diperbarui, dalam contoh ini $w$. Proses mencari turunan inilah yang lebih tepat disebut backpropagation. Karena ada banyak nilai $w$, kita akan spesifikkan untuk mengupdate nilai $w_{11}$ terlebih dulu. Setelahnya, kita akan coba hitung update nilai untuk $b_1$.

Konsep chaining

Untuk menghitung $ \frac{\partial E}{\partial w} $, pertama-tama kita coba berjalan mundur dulu. Urutan proses backward chaining digambarkan dengan garis merah pada gambar di bawah ini. Dari mana nilai $E$ didapatkan dan apa hubungannya dengan $w_{11}$.

Nilai $E$ diperoleh dari rumus Mean Square Error:

$$ E = \frac{1}{2}((t_1 – y_1)^2+(t_2 – y_2)^2) $$

dari rumus di atas tidak ada variabel $w_{11}$ tetapi kita bisa coba “jalan mundur” lagi. Kita ingat-ingat lagi dari mana nilai setiap variabel $y$ berasal.

$$ \begin{eqnarray}
y_1 & = \sigma \left ( z_1 \right) \nonumber \\
y_2 & = \sigma \left ( z_2 \right) \nonumber \end{eqnarray}$$

Variabel $y$ diperoleh dari menerapkan sebuah fungsi aktivasi terhadap variabel $z$. Sedangkan, variabel $z$ sendiri dihitung dengan:

$$\begin{eqnarray} z_1 = w_{11}x_{1} + w_{21}x_{2} + w_{31}x_{3} + b_1\\ z_2 = w_{12}x_{1} + w_{22}x_{2} + w_{32}x_{3} + b_2 \end{eqnarray}$$

dari sini terlihat variabel $w_{11}$ ada di perhitungan $z_1$ yang secara tidak langsung berpengaruh ke nilai $E$. Hal ini yang disebut dengan chaining atau rantaian.

Dasar turunan

Setelah kita memahami hubungan $E$ dan $w_{11}$ langkah selanjutnya adalah kita pahami bagaimana dasar menghitung turunannya. Disini kita menggunakan turunan parsial yang bedanya dengan turunan biasa adalah fungsi bisa mengandung lebih dari satu variabel. Selain itu, kita tidak menggunakan simbol $d$ tetapi turunan parsial menggunakan simbol $\partial$. Dari sekian banyak materi turunan jaman SMA kita cukup mengingat beberapa aturan saja (aturan no. 5 tidak diajarkan di SMA):

  1. jika $f(x) = x^n$ maka $\frac{\partial f(x)}{\partial x} = nx^{n-1}$, sudah cukup jelas, ini adalah rumus dasar turunan.
  2. jika $f(x) = u(x) + v(x)$ maka $\frac{\partial f(x)}{\partial x} = \frac{\partial u(x)}{\partial x} + \frac{\partial v(x)}{\partial x}$, artinya jika ada sebuah fungsi $f$ yang isinya adalah jumlahan dari fungsi-fungsi lain, kita bisa turunkan masing-masing lalu dijumlahkan.
  3. jika $f(x, y) = u(x) + v(y)$ maka $\frac{\partial f(x)}{\partial x} = \frac{\partial u(x)}{\partial x} + 0$, sama dengan poin no.2, hanya saja jadi keliatan ketika ada bagian dari fungsi $f$ yang ternyata tidak mengandung variabel yang ingin diturunkan (yakni $x$) maka fungsi tersebut bisa dijadikan 0.
  4. jika $f(x) = f(g(x))$ maka $\frac{\partial f(x)}{\partial x} = \frac{\partial f(x)}{\partial g(x)} \cdot \frac{\partial g(x)}{\partial x}$, jika ada fungsi yang di dalamnya ada fungsi lain, bisa dilakukan turunan untuk masing-masingnya lalu dikalikan
  5. jika $f(x) = \sigma(x)$ dengan $\sigma(x)$ adalah fungsi sigmoid, maka $\frac{\partial f(x)}{\partial x} = f(x)(1- f(x))$.

Contoh:

  1. $f(x)=2x^3$ maka turunan $\frac{\partial f(x)}{\partial x} = 6x^{2}$
  2. $f(x)=2x^3 + x^2$ maka turunan $\frac{\partial f(x)}{\partial x} = 6x^{2} + 2x$
  3. $f(x,y)=2x^3 + y^2$ maka turunan $\frac{\partial f(x,y)}{\partial x} = 6x^{2} + 0$
  4. $f(x)=z^2$ dimana $z$ dihitung dari $z=2x^3$ maka turunannya:
    $\frac{\partial f(x)}{\partial x} = \frac{\partial f(x)}{\partial z} \cdot \frac{\partial z}{\partial x}$
    $\frac{\partial f(x)}{\partial x} = 2z \cdot \frac{\partial z}{\partial x}$
    $\frac{\partial f(x)}{\partial x} = 2z \cdot 6x^2 = 2(2x^3) \cdot 6x^2 = 24x^5$

Menghitung turunan

Update nilai $w_{11}$

Nah, mari kita menghitung nilai $ \frac{\partial E}{\partial w} $ dengan beberapa langkah menggunakan aturan perhitungan yang disebutkan sebelumnya. Menggunakan aturan no. 4 di atas, kita bisa mencari nilai $ \frac{\partial E}{\partial w_{11}} $ dengan 2 langkah berikut:

$$ \frac{\partial E}{\partial w_{11}} = \color{#6bb9cfff}{ ( } \frac{\partial E}{\partial y_1} \color{#6bb9cfff}{)} \cdot \color{#46ce8eff} {(} \frac{\partial y_1}{\partial w_{11}} \color{#46ce8eff} {)} $$

Langkah 1

Kita selesaikan bagian pertamanya, menggunakan aturan no. 3 dan no. 4 di atas, maka:

$$ \begin{eqnarray}
& E &= \frac{1}{2}((t_1 – y_1)^2+(t_2 – y_2)^2) \nonumber \\
& \frac{\partial E}{\partial y_1} & = 2 * \frac{1}{2}(t_1 – y_1)^{2-1}-1+ 0 \nonumber \\
& & = – (t_1 – y_1) \nonumber \end{eqnarray}$$

Langkah 2
Untuk bagian keduanya kita lihat kembali rumus asli untuk menghitung $y_1$, yakni dengan menggunakan fungsi sigma terhadap $z_1$ :

$$ y_1 = \sigma(z_1) $$

$$ z_1 = w_{11}x_{1} + w_{21}x_{2} + w_{31}x_{3} + b_1 $$

Variabel $w_{11}$ tidak langsung ditemukan dalam perhitungan variabel $y_1$, melainkan perlu mundur lagi ke variabel $z_1$. Dengan aturan no. 4, maka pada tahap ini kita bisa memecah $\frac{\partial y_1}{\partial w_{11}}$ menjadi 2 bagian lagi:

$$ \frac{\partial y_1}{\partial w_{11}} = \color{#ff6900}{(} \frac{\partial y_1}{\partial z_1} \color{#ff6900}{)} \cdot \color{#f78da7}{(} \frac{\partial z_1}{\partial w_{11}} \color{#f78da7}{)}$$

Kita selesaikan bagian pertama $\frac{\partial y_1}{\partial z_1}$ dengan aturan no. 5:

$$ \begin{eqnarray}
& y_1 &= \sigma(z_1) \nonumber \\
& \frac{\partial y_1}{\partial z_1} &= y_1 ( 1 – y _1) \end{eqnarray}$$

Kemudian untuk bagian kedua $\frac{\partial z_1}{\partial w_{11}}$ kita selesaikan menggunakan aturan no. 2 dan no. 3, menjadi:

$$ \begin{eqnarray}
& z_1 &= w_{11}x_{1} + w_{21}x_{2} + w_{31}x_{3} + b_1 \nonumber \\
& \frac{\partial z_1}{\partial w_{11}} &= x_{1} + 0 + 0 + 0 \nonumber \\
& &= x_1 \end{eqnarray}$$

Gabungkan semua
Secara ringkas dari perhitungan-perhitungan di atas, maka nilai dari $ \frac{\partial E}{\partial w_{11}} $ adalah:

$$ \begin{eqnarray}
& \frac{\partial E}{\partial w_{11}} &= \color{#6bb9cfff}{ ( }\frac{\partial E}{\partial y_{1}}\color{#6bb9cfff}{ ) } \cdot \color{#46ce8eff} {(} \space \color{#ff6900}{(} \frac{\partial y_1}{\partial z_{1}} \color{#ff6900}{)} \cdot \color{#f78da7}{(} \frac{\partial z_1}{\partial w_{11}} \color{#f78da7}{)} \space \color{#46ce8eff} {)} \nonumber \\
& &= – (t_1 – y_1) \cdot y_1 ( 1 – y _1) \cdot x_1
\end{eqnarray}$$

Jika diinputkan dengan angka maka:

$$ \begin{eqnarray}
& \frac{\partial E}{\partial w_{11}} &= – (t_1 – y_1) * y_1 ( 1 – y _1) * x_1 \nonumber \\
& & = – (0 – 0.721) * 0.721 ( 1 – 0.721) * 1 \\
& & = 0.1587 \end{eqnarray}$$

Sehingga untuk memperbarui bobot $w_{11}$ nilai yang baru dengan nilai $\alpha=0.5$ (contoh) adalah:

$$ \begin{eqnarray}
& w_{11new} &= w_{11old} – \alpha \frac{\partial E}{\partial w_{11}} \nonumber \\
& &= 0.2 – (0.5)(0.1587) \nonumber \\
& &= 0.1206 \end{eqnarray}$$

Update nilai $b_1$

Chaining untuk mengupdate nilai bias dilakukan serupa dengan cara mengupdate nilai bobot. Mulai dari paling belakang, telusuri tiap variabel dan pecah menurut perhitungan rumusnya, sampai ditemukan variabel bias yang ingin diupdate. Untuk mengupdate bias $b_1$, dapat dihitung dengan :

$$ \frac{\partial E}{\partial b_{1}} = \color{#6bb9cfff}{ ( } \frac{\partial E}{\partial y_1} \color{#6bb9cfff}{)} \cdot \color{#46ce8eff} {(} \frac{\partial y_1}{\partial b_{1}} \color{#46ce8eff} {)} $$

Perhatikan bahwa bagian pertama $\frac{\partial E}{\partial y_1}$, dengan kurung berwarna biru, telah kita hitung sebelumnya pada contoh update bobot $w_{11}$. Bagian ini menghasilkan $\frac{\partial E}{\partial y_1} = – (t_1 – y_1)$.

Selanjutnya kita fokus ke bagian kedua $\frac{\partial y_1}{\partial b_{1}}$ dengan kurung berwarna hijau. Variabel $b_1$ dapat diperoleh dengan merunut jalur variabel $y_1$ kemudian ke variabel $z_1$ (perhatikan ilustrasi jalur backward chaning dengan garis merah putus-putus pada gambar sebelumnya).

$$ y_1 = \sigma(z_1) $$

$$ z_1 = w_{11}x_{1} + w_{21}x_{2} + w_{31}x_{3} + b_1 $$

Perhatikan bahwa jalur ini juga sama dengan yang dilalui untuk mencari update bobot $w_{11}$, yakni dengan memecah menjadi dua bagian berikut:

$$ \frac{\partial y_1}{\partial b_1} = \color{#ff6900}{(} \frac{\partial y_1}{\partial z_1} \color{#ff6900}{)} \cdot \color{#f78da7}{(} \frac{\partial z_1}{\partial b_1} \color{#f78da7}{)}$$

Bagian pertama $\frac{\partial y_1}{\partial z_1}$, tidak perlu dihitung lagi karena sudah pernah kita hitung saat proses update $w_{11}$, yakni $\frac{\partial y_1}{\partial z_1} = y_1 ( 1 – y _1)$. Kemudian bagian kedua $\frac{\partial z_1}{\partial b_1}$ adalah:

$$ \begin{eqnarray}
& z_1 &= w_{11}x_{1} + w_{21}x_{2} + w_{31}x_{3} + b_1 \nonumber \\
& \frac{\partial z_1}{\partial b_1} &= 0 + 0 + 0 + 1 \nonumber \\
& &= 1 \end{eqnarray}$$

Gabungkan semua
Setelah semua variabel pada jalur chaining dapat dipecah dan berakhir pada bias $b_1$, maka dapat kita gabungkan menjadi:

$$ \begin{eqnarray}
& \frac{\partial E}{\partial b_1} &= \color{#6bb9cfff}{ ( }\frac{\partial E}{\partial y_{1}}\color{#6bb9cfff}{ ) } \cdot \color{#46ce8eff} {(} \space \color{#ff6900}{(} \frac{\partial y_1}{\partial z_{1}} \color{#ff6900}{)} \cdot \color{#f78da7}{(} \frac{\partial z_1}{\partial b_1} \color{#f78da7}{)} \space \color{#46ce8eff} {)} \nonumber \\
& &= – (t_1 – y_1) \cdot y_1 ( 1 – y _1) \cdot 1
\end{eqnarray}$$

Jika diinputkan dengan angka:

$$ \begin{eqnarray}
& \frac{\partial E}{\partial b_1} &= – (t_1 – y_1) * y_1 ( 1 – y _1) * 1 \nonumber \\
& & = – (0 – 0.721) * 0.721 ( 1 – 0.721) * 1 \\
& & = 0.1587 \end{eqnarray}$$

Sehingga untuk memperbarui bias $b_1$ yang baru dengan nilai $\alpha=0.5$ (contoh) adalah:

$$ \begin{eqnarray}
& b_{1new} &= b_{1old} – \alpha \frac{\partial E}{\partial b_1} \nonumber \\
& &= 0 – (0.5)(0.1587) \nonumber \\
& &= -0.0793 \end{eqnarray}$$

Mengupdate semua bobot

INGAT! perhitungan di atas belum selesai memperbarui semua bobot dan bias. Saat backpropagation, proses di atas kita lakukan ke semua bobot $w$ dan bias $b$.

Tetapi jangan takut, karena sudah dapat rumus turunannya, kita bisa langsung lihat pola rumusnya. Misalnya untuk $w_{21}$ kita bisa cukup mengubah bagian nilai $\frac{\partial z_1}{\partial w_{21}}$ ketika menghitung turunan (karena $w_{21}$ masih sama-sama bagian dari $y_1$).

$$ \begin{eqnarray}
& \frac{\partial E}{\partial w_{21}} &= \frac{\partial E}{\partial y_{1}} \cdot \frac{\partial y_1}{\partial z_{1}} \cdot \frac{\partial z_1}{\partial w_{21}} \nonumber \\
& &= – (t_1 – y_1) * y_1 ( 1 – y _1) * x_2 \nonumber \\
& & = – (0 – 0.721) * 0.712 ( 1 – 0.721) * 2 \\
& & = 0.317 \end{eqnarray}$$

$$ \begin{eqnarray}
& w_{21new} &= w_{21old} – \alpha \frac{\partial E}{\partial w_{21}} \nonumber \\
& &= 0.3 – (0.5)(0.317) \nonumber \\
& &= 0.141 \end{eqnarray}$$

Namun, agak berbeda jika kita ingin memperbarui nilai $w_{12}$ hal ini karena jika diperhatikan $w_{12}$ tidak ikut membangun nilai $y_1$ tetapi berada di perhitungan $y_2$. Berikut ilustrasinya:

Maka untuk menghitung turunannya menjadi sedikit beda:

$$ \begin{eqnarray}
& \frac{\partial E}{\partial w_{12}} &= \frac{\partial E}{\partial y_{2}} \cdot \frac{\partial y_2}{\partial z_{2}} \cdot \frac{\partial z_2}{\partial w_{12}} \nonumber \\
& &= -(t_2 – y_2) * y_2 ( 1 – y _2) * x_1 \nonumber \\
& & = -(0 – 0.645) * 0.645 ( 1 – 0.645) * 1 \nonumber \\
& & = -0.0107 \end{eqnarray}$$

$$ \begin{eqnarray}
& w_{12new} &= w_{12old} – \alpha \frac{\partial E}{\partial w_{12}} \nonumber \\
& &= 0.3 – (0.5)(-0.0799) \nonumber \\
& &= 0.3399 \end{eqnarray}$$

Evaluasi

Setelah melakukan backpropagation untuk semua bobot dan bias, maka akan diperoleh hasil bobot sebagai berikut:

$$ \begin{bmatrix}
w_{11} = 0.1206 & w_{12} = 0.3399 \\
w_{21} = 0.1412 & w_{22} = 0.1799 \\
w_{31} = 0.2603 & w_{32} = 0.2199 \\
\end{bmatrix} $$

$$ [b_1=-0.0793, b_2 = 0.0399]$$

Untuk mengevaluasi kita bisa mengecek kembali hasilnya dengan forward propagation (tanpa perlu backpropagation). Jika kita lakukan forward propagation, maka akan diperoleh nilai $y$ sebagai berikut:

$$ [y_1=0.6115, y_2 = 0.7005]$$

Jika kita hitung errornya maka akan terjadi perubahan nilai dari sebelum dilakukan backpropagation. Nilai error telah menjadi lebih kecil dari sebelumnya (error sebelumnya 0.3227):

$$\begin{eqnarray}
& E & = \frac{1}{3} \sum_{i=1}^2 (target_i – prediksi_i)^2 \nonumber \\
& & = \frac{1}{3}((t_1 – y_1)^2+(t_2 – y_2)^2) \nonumber \\
& & = \frac{1}{3}((0 – 0.6115)^2+(1 – 0.7005)^2) \nonumber \\
& & = 0.2318 \nonumber \
\end{eqnarray}$$

Hal tersebut menandakan backpropagation kita telah berhasil 🙂

Perlu dicatat, bahwa proses di atas adalah proses iterasi 1 kali backpropagation dan untuk 1 data. Jika ada banyak data, maka proses di atas bisa diulang lagi dengan data yang berbeda dan mengupdate bobotnya lagi. Lalu diulang untuk semua data (beberapa epoch) hingga mendapatkan hasil yang optimal dan juga dilakukan untuk banyak data.

Proses implementasi akan dibahas di post selanjutnya insyaAllah. Sekian, jika ada yang ditanyakan seputar rumus atau perhitungannya, silakan bertanya di kolom komentar 😉 Terima kasih

Sumber gambar: flickr
artikel ini terinspirasi dari artikel Matt Mazur

About the author

Rian Adam

Lecturer at Universitas Islam Indonesia; Machine Learning Enthusiast

View all posts

37 Comments

  • maaf mau tanya, untuk nilai bias [b1=−0.19,b2=1.01,b3=1.95] ini di dapat dari hasil mana? atau random saja ya mas?

    • Itu adalah bias hasil backpropagation, dihitung menggunakan cara yang mirip dengan peng-update-an bobot. Mungkin untuk detailknya saya akan coba tambahkan penjelasannya di artikel

    • Adam merupakan pengembangan dari gradient descent standard, khususnya pada pengaturan learning rate yang dapat berubah (adaptive). Mohon maaf untuk saat ini kami belum bisa menjelaskan Adam secara detail, insyaAllah jika ada kesempatan akan kami bahas lebih detail di artikel. Untuk referensi lebih lanjut, kami sarankan ke artikel oleh Sebastien Ruder yang membandingkan semua pengembangan algoritma gradient descent: https://arxiv.org/abs/1609.04747

  • pada proses Forward Propagation, didalam perhitungan menentukan nilai y, simbol sigma kan berarti fungsi aktivasi sigmoid, dari hasil “sigma(0.95)” bisa menjadi 0.72 itu bagaimana proses hitungnya ? mohon bantuannya

  • Sangat bermanfaat sekali pak

    Mau bertanya pak , jika parameter pembelajaran di tambahkan koefesien momentum

    Rumus untum pengupdate an bobot nya jadi seperti apa yah pak ?

    Terimakasih pak

  • Mau bertanya pak, untuk menentukan bobot awal dan bias itu gimana pak saya masih bingung dengan penjelasan di atas, misal input layer 12, hidden layer 10, output layer 1

    • Pada contoh di atas, penentuan bobot dan bias awal diberi secara random. Tetapi di luar sana ada banyak penelitian yang mengusulkan metode untuk menentukan nilai awal bobot dan bias.

    • Halo, secara umum perhitungan dilakukan dengan konsep BPTT (Backpropagation Through Time). Untuk ukuran timestep n, turunan error dihitung untuk tiap timestep t, dari timestep terakhir t=n sampai timestep pertama t=0. Perhitungan turunan error menggunakan chain rule yang melibatkan turunan dari bobot W, U, b pada masing-masing gate f, a, i, o. Setelah perhitungan sampai pada timestep t=0, seluruh bobot pada sel LSTM diupdate dengan mengakumulasi semua perubahan bobot yang telah dihitung di tiap timestep.

      Insyaallah contoh perhitungan backpropagation pada LSTM akan segera kami bahas di artikel tersendiri. Untuk sementara, kami sarankan membaca artikel oleh Aidan Gomez berikut: https://blog.aidangomez.ca/2016/04/17/Backpropogating-an-LSTM-A-Numerical-Example/

  • Terimakasih, penjelasannya sangat bagus. sy mw bertanya, Bagaimana cara mendapatkan nilai bias baru, b1=-0.19, b2=1.01, b3=1.95. mohon penjelasannya. terimakasih

    • Terima kasih atas pertanyaannya, mohon maaf ada kesalahan perhitungan untuk nilai bias baru dan sudah kami perbaiki di artikel.

      Cara perhitungan update bias sama persis dengan langkah-langkah untuk mengupdate bobot w (contoh di artikel, w11). Misalnya, rumus update bias b1 new = b1 old – (alfa * delta E/delta b1). Perlu diperhatikan, bahwa saat menghitung nilai turunan delta z/delta b1, tidak ada variabel pengali lain terhadap variabel bias b1, maka nilai turunannya adalah 1. Ini berbeda dengan update bobot w11. Pada saat mencari turunan delta z/delta w11, ada variabel x1 sehingga nilai turunannya adalah x1.

      • terimakasih atas penjelasannya, tapi maaf saya kurang faham dengan yg dijelaskan pada update bias | b1 new = b1 old – (alfa * delta E/delta b1). |
        casenya seperti ini; learning rate/alfa = 0.5, bias = 1, lalu misalkan total data di setiap 1 iterasi/epoch ada 10.

        yg saya faham disini.. untuk iterasi/epoch pertama jika menggunakan jika menggunakan rumus yg anda jelaskan apakah hasilnya seperti ini ::
        bias data k1 = 0.5 – (1 – 1) = 0.5,
        bias data k2 = 0.5 – (0.5 – 1) = 0,
        bias data k3 = 0 – (0.5 – 1) = -0.5,
        bias data k4 = -0.5 – (0 – 1) = -1,
        bias data k5 = -1 – (-0.5 – 1) = -1.5,
        dan seterusnya..

        apakah seperti itu?

  • Tolong kak repost perhitungan manual yg sebelum diupdate ini pada artikel diatas yg memberikan contoh output 3 node

  • terimakasih, penjelasaanya saangat detail dan membantu bagi saya
    mau tanya pak, kalo untuk penentuan bias dan bobot nya itu kan bapak info diatas “random” ya
    apakah se random”nya tetep ada ketentuan? contohnya angka bias dan bobot harus kurang dari 1. karena saya liat bapak pakai angka kurang dari 1

    • Sepertinya kami tidak akan merepost versi lama, karena di versi lama terdapat beberapa kesalahan perhitungan. Untuk versi ini apakah ada kesulitan? karena di versi lama perhitungan 3 node output tidak berbeda dengan versi ini

      • Saya mau tanya, utk menghitung Mean Square Error apabila apabila outpunya 2 node kan seperti ini : 1/2 (y1-t1)^2 + (y2-t2)^2

        Tapi bila outputnya ada 3 node apkah akan mjd seperti ini? 1/3 (y1-t1)^2 + (y2-t2)^2 + (y3-t3)^2

        Atau bgmna?

        • iya benar, 1/2 di awal itu tujuannya untuk merata-rata (mean). Ketika nodenya 3 maka di kali 1/3. Jadi 1/3((y1-t1)^2 + (y2-t2)^2 + (y3-t3)^2)

          *perhatikan tanda kurungnya ya

          • Terimakasih kak, saya paham skrg, jarang sekali yg memposting perhitungan manual ANN yg begitu rinci semacam ini, hanya di blog ini dan satu lagi punyanya Matt Mazur.

            Maaf saya masih n00b tentang ANN, saya mencoba mempelajarinya utk mengaplilasikannya dalam Deep Q Network.

  • Maaf mas saya mau tanya, jika diberikan input baru setelah proses backpro dijalankan. Apakah weight yang digunakan itu langsung dari bobot yang telah diupdate?

    • Setahu saya sih begitu, tp backprop dilakukan berulang2 hingga max epoch dan/atau min error yg ditentukan telah tercapai, weight akan terupdate setiap 1 epoch, 1 epoch = 1xforwardprop dan 1xbackprop.

      Pada project yg saya buat algoritma akan mengulang backprop hingga min error tercapai misal 0.0000001, lalu baru saya ijinkan utk membaca input baru. Semoga sdkit menjawab

    • Kalau di artikel ini, ya benar, untuk satu (1) data -> forward -> hitung (1) error -> backprop dan update bobot (disebut SGD / Stochastic Gradient Descent).

      Tapi implementasinya, ada metode lain misal Batch dan Minibatch Gradien Descent.
      Batch: semua (N) data diproses forward -> hitung rata-rata (N) error -> backprop dan update bobot
      Minibatch: beberapa (n < N) data diproses forward -> hitung rata-rata (n) error -> backprop dan update bobot

      Jadi tergantung menggunakan metode optimisasi apa

  • hallo kak saya mau bertanya tentang estimasi menggunakan metode ini
    saya punya data X=ukuran rumah dan Y=harga rumah ada 10 data
    nah kemudian pertanyaannya kita harus estimasi harga rumah dengan ukuran 2000, saya belum paham untuk menentukan bobot dan hiden layer nya, kemudian cara mendapat hasil estimasinya gimana serta menghitung manual iterasi yg dibutuhkan untuk mendapat hasil yg paling baik, terimakasih

    • Y (harga rumah), asumsi saya nilainya seperti harga pada umumnya, bervariasi kan ya? Kalau ya, berarti ini problem prediksi numerik. Berbeda dengan contoh di artikel, problemnya klasifikasi atau prediksi kategorik.

      Prediksi numerik dengan JST, jumlah neuron output diubah menjadi 1 saja. Proses forward sama seperti pada artikel ini, namun tanpa fungsi aktivasi sigmoid. Error dihitung antara Ypred (hasil forward pada neuron output) dengan Y (harga asli).

      Penentuan bobot random saja. Jumlah hidden layer bisa dicoba-coba (bagian dari eksperimen). Misal coba 1 hidden layer dulu, lakukan forward dan bakcprop ke semua data, ulangi beberapa epoch. Kemudian coba ulangi dari awal dengan 2 hidden layer, dst.

      Hasil yang baik, adalah ketika error sudah minimal. Jika belum, bisa lanjutkan pelatihan dengan menambah jumlah epoch.

      Estimasi harga, diketahui ukuran 2000. Diperoleh dengan menghitung forward sampai neuron output, menggunakan bobot terakhir yang diperoleh dari hasil pelatihan.

  • Hallo kak saya mau bertanya. Saya sedang melakukan penelitian klasifikasi penyakit dengan menggunakan backpropagation. Penyakit yang saya klasifikasikan adalah penyakit dengan gejala demam ke dalam tiga kelas yaitu DBD, Tifoid dan Malaria. Bagaimana cara menentukan skor gejala dari penyakit tersebut? Dan bagaimana juga mendefinisikan outputnya? Mohon bantuannya kak.

    • maksudnya skor gejala?

      karena ini kasus klasifikasi dengan 3 kelas, maka bisa menggunakan 3 neuron pada output layer. Lalu cara termudahnya bisa dengan memilih neuron dengan nilai output terbesar di antara 3 neuron tersebut sebagai kelas yang dipilih

      • Maksudnya skor gejala adalah pendefenisian inputnya kak. Misalnya untuk gejala “demam intermitten (x1)” nilai bobotnya berapa, dan untuk penentuan nilai outputnya bagaimana kak?
        Misalnya kita buat nilai output -1 adalah DBD, 0 adalah Tifoid dan 1 adalah Malaria. Apakah bisa kiya buat juga untuk nilai -1 Tifoid, 0 Malaria dan 1 DBD?

        Apa yang mendasari pemberian nilai output tersebut gitu kak?
        Mohon bantuannya kak

Leave a Reply