linear-regression-everywhere

Tulisan ini adalah seri kedua dari rangkaian proyek mengimplementasikan dan menulis algoritma machine learning (hampir) dari awal. Tulisan pertama dari seri ini adalah Build a Simple K-Nearest Neighbor Algorithm (Almost) from Scratch. Pada tulisan kali ini, kita akan coba fokus untuk membangun algoritma model linear regression.


Sama seperti KNN, linear regression adalah salah satu algoritma supervised learning yang paling dasar, dimana algoritma ini digunakan untuk memprediksi nilai output kontinyu berdasarkan satu atau lebih nilai input. Prinsip dasarnya cukup sederhana, yaitu mencari hubungan linear antara variabel independen (input) dan variabel dependen (output).

Adapun linear regression akan bekerja berdasarkan persamaan linear berikut:

dimana:

  • y adalah variabel dependen atau nilai yang ingin kitap prediksi,
  • Xi adalah variabel independen,
  • βi adalah koefisien untuk variabel independen,
  • β0 adalah intercept.

regression

Nah, di dalam kontek algoritma linear regression kita nanti, kita akan mencari nilai β yang meminimalkan residual sum of squares (RSS), yaitu varians error dari output prediksi model kita. Source code untuk algoritma linear regression kita akan kita tulis di dalam base.py yang ada di dalam direktori linear.

ml_from_scratch/ 
├── neighbors
├── linear/ 
│ ├── __init__.py 
│ └──  base.py 

Nantinya, di dalam direktori ini kita juga akan menyimpan beberapa source code dari pengembangan base model kita, seperti regularisasi dan logistic regression. Namun untuk sekarang, kita hanya akan fokus ke base model lebih dulu. Sudah siap? Mari kita mulai!


Pseudocode Base Model

Sebelum menulis source code untuk algoritma base linear regression kita, salah satu best practice yang direkomendasikan banyak orang adalah menulis pseudocode kita lebih dulu. Berdasarkan pemahaman mengenai linear regression, kita dapat menulis pseudocode untuk kelas kita nantinya kurang lebih seperti berikut:

baseLinearRegression:
    Fungsi __init__(self, fit_intercept=True):
        Inisialisasi intercept dan koefisien
        Tentukan apakah model harus mencakup intercept atau tidak

    Fungsi fit(self, X, y):
        Ubah X dan y menjadi array numpy jika belum
        Jika fit_intercept == True, maka kita akan tambahkan kolom ones ke X
        Hitung koefisien
        Pisahkan intercept dari koefisien jika fit_intercept True

    Fungsi predict(self, X):
        Hitung prediksi y menggunakan model linier

Nah, setelah kita menyusun pseudocode seperti di atas, kita dapat pelan-pelan membangun kelas kita untuk algoritma linear regression ini.

Implementasi dari Pseudocode

Setelah memahami dan melalui beberapa kali iterasi, kita dapat menerjemahkan pseudocode kita ke dalam sebuah kelas dengan menggunakan Python seperti berikut ini:

import numpy as np
import pandas as pd


class baseLinearRegression:
    def __init__(self, fit_intercept=True):
        # inisialisasi setup
        self.coef_ = None
        self.intercept = None
        self.fit_intercept = fit_intercept

    # *************************************
        
    def fit(self, X, y):
        # handling different data type input
        if isinstance(X, pd.DataFrame):
            X = X.values
        else:
            X = np.array(X)
        if isinstance(y, pd.Series):
            y = y.values
        else:
            y = np.array(y)
        
        # buat design matrix A
        if self.fit_intercept:
            A = np.c_[np.ones((X.shape[0], 1)), X]
        else:
            A = X

        # hitung optimal coefficients 
        theta = np.linalg.inv(A.T @ A) @ A.T @ y

        # extract parameter
        if self.fit_intercept:
            self.intercept = theta[0]
            self.coef_ = theta[1:]
        else:
            self.intercept = 0.0
            self.coef_ = theta

    # *************************************
    
    def predict(self, X):
        # handling different data type input
        if isinstance(X, pd.DataFrame):
            X = X.values
        else:
            X = np.array(X)

        y_pred = np.dot(X, self.coef_) + self.intercept

        return y_pred

Dengan pengimplementasian ini, kita setidaknya sudah dapat memodelkan hubungan antara variabel independen dan dependen serta melakukan prediksi ketika terdapat data point baru. Selanjutnya, kita akan menguji kelas ini dengan kasus regresi sederhana.

Pengujian baseLinearRegression

Pada bagian ini kita akan coba menguji baseLinearRegression yang telah kita tulis sebelumnya. Kita akan menggenerate dataset linear sederhana untuk melihat apakah model kita sudah cukup memenuhi ekspektasi kita untuk dapat memodelkan hubungan linear antar feature dan target variable.

np.random.seed(42)

# generate random data
X = 2 * np.random.rand(100, 1)
y = 4 + 3 * X + np.random.randn(100, 1)

plt.figure(figsize=(6,5))
plt.scatter(X, y)
plt.xlabel('Feature')
plt.ylabel('Target')
plt.title('Dummy Linear Dataset')
plt.show()

dummy

Setelah kita mempunyai dataset di atas, kita bisa mencoba menggunakan baseLinearRegression dan fit model ini ke dataset yang kita punya dan juga membuat prediksi ke data point baru atau data eksisting kita.

model = baseLinearRegression()
model.fit(X, y)

# generate test data untuk prediksi
X_test = np.linspace(X.min(), X.max(), 100).reshape(-1, 1)
y_pred = model.predict(X_test)

# plot original data dan hasil model
plt.figure(figsize=(6,5))
plt.scatter(X, y, label='Original data')
plt.plot(X_test, y_pred, color='red', label='Fitted line')
plt.xlabel('Feature')
plt.ylabel('Target')
plt.title('baseLinearRegression Model Fit')
plt.legend()
plt.show()

model-fit

Dengan memvisualisasikan hasil prediksi model kita, kita dapat melihat seberapa fit line prediksi kita terhadap data point yang ada. Selain dengan memvisualisasikannya, tentu kita juga dapat menggunakan beberapa metrik seperti mean squared error atau MSE untuk mengevaluasi performa dari model tersebut dengan membandingan nilai prediksi dengan nilai aktual target.


Meskipun cukup sederhana, dengan menulis dan mengimplementasikan sendiri linear regression seperti di atas, harapannya adalah kita dapat memiliki pemahaman yang lebih dalam lagi bagaimana model bekerja dan bagaimana bisa diaplikasikan ke dalam berbagai kasus yang lebih kompleks.

Silahkan kunjungi laman LinkedIn untuk bisa berkoneksi ataupun berkomunikasi lebih lanjut.