Kenang Laverda & Muhammad Fitrah
Departemen Statistika, Fakultas Sains dan Analitika Info, Institut Teknologi Sepuluh Nopember Surabaya, Indonesia
ABSTRAK
Australia adalah benua yang dikenal dengan iklim ekstrem dan variabilitas cuaca yang tinggi, di mana curah hujan mempengaruhi berbagai sektor seperti pertanian, pengelolaan sumber daya air, dan perencanaan kota. Prediksi hujan yang akurat sangat penting untuk mendukung aktivitas tersebut. Penelitian ini memanfaatkan machine finding out untuk memprediksi kejadian hujan di Australia menggunakan dataset “Rain in Australia” dari Kaggle. Empat metode klasifikasi yang dianalisis meliputi Logistic Regression, Random Forest, Extreme Gradient Boosting (XGBoost), dan Dedication Tree. Hasil evaluasi menunjukkan bahwa XGBoost memberikan performa terbaik dengan akurasi 89.8% dan F1 Score 88.73%, serta waktu pemrosesan yang efisien sebesar 1.71 detik. Oleh karena itu, XGBoost disarankan sebagai model utama untuk prediksi hujan di Australia. Penelitian ini juga menekankan pentingnya optimasi hyperparameter lebih lanjut dan evaluasi berkelanjutan dengan dataset yang lebih besar dan bervariasi untuk memastikan model tetap sturdy dan andal dalam berbagai kondisi cuaca. Hasil penelitian ini diharapkan dapat memberikan kontribusi signifikan dalam perencanaan dan pengelolaan sumber daya yang lebih baik di Australia.
Halo semua, kali ini saya akan melakukan penerapan metode analisis klasifikasi dengan menggunakan dataset “Rain in Australia”. Metode yang digunakan antara lain Dedication Tree, Random Forest, XGBoost, dan Regesi Logistik. Untuk output dari penerapan ini adalah menentukan metode mana yang terbaik untuk digunakan dalam studi kasus ini.
Dataset ini terdapat sebanyak 19 variabel yang berisi variabel proceed, diskrit, maupun kategorik. Langkah pertama yang dapat dilakukan adalah
1. IMPORT DATA
# importing libraries# primary objective libraries
import numpy as np
import pandas as pd
# for visualization
import matplotlib.pyplot as plt
import seaborn as sns
# for statical analysis
import time
from statsmodels.stats.outliers_influence import variance_inflation_factor
# for preprocessing
from sklearn.preprocessing import StandardScaler , LabelEncoder
# for apply verify reduce up
from sklearn.model_selection import train_test_split
# for oversampling
from imblearn.over_sampling import SMOTE
# for fashions
from sklearn.linear_model import LogisticRegression
from sklearn.ensemble import RandomForestClassifier
from xgboost import XGBClassifier
# for evaluation
from sklearn.metrics import accuracy_score , classification_report , confusion_matrix , recall_score , precision_score , f1_score
%matplotlib inline
# to cowl any warnings
import warnings
warnings.filterwarnings('ignore')
# to confirm the entire columns are displayed
pd.set_option('present.max_columns' , None)
# Load the dataset
df = pd.read_csv('Info FP SML.csv', sep=';', header=0)
# Preview the dataset
df.head()
2. CEK TIPE DATA
# checking data kinds of columns
df.dtypesdf['Pressure3pm'] = pd.to_numeric(df['Pressure3pm'], errors='coerce')
# checking data kinds of columns
df.dtypes
3. Pre-Processing (Penanganan Missing Price, Outlier, Inbalance Info, dan Korelasi)
# take a look at for missing values
df.isna().sum()
# Get distinctive enteries from Location column of the dataset
unique_location = df['Location'].distinctive()# Iterate over each column with missing values which have numeirc data kind
for column in df.select_dtypes(exclude='object'):
# establishing a state of affairs to check missing values
if df[column].isnull().any():
# Iterate over each distinctive location
for location in unique_location:
# Calculate the median price for the each distinctive location entry and column
location_median = df[df['Location'] == location][column].median()
# Fill missing values with the medin of the exact location
df.loc[df['Location'] == location, column] = df[df['Location'] == location][column].fillna(location_median)
# iterate over each column with misssing values which have object data kind
elif df.select_dtypes(embody='object'):
# iterate over each distinctive location
for location in unique_location:
# Calculate the median price for the each distinctive location entry and column
location_mode = df[df['Location'] == location][column].mode()[0]
# Fill missing values with the mode of the exact location
df.loc[df['Location'] == location , column ] = df[df['Location']==location][column].fillna(location_mode)
# dropping the rows with missing values
df.dropna(subset=['WindGustDir','WindGustDir' ,'WindDir9am','WindDir3pm','RainToday' ,'RainTomorrow',"Pressure9am","Pressure3pm"
], inplace=True , axis= 0)
# resetting the index of the dataframe
df.reset_index(drop=True , inplace=True)
# confirming the tip consequence
df.isnull().sum()
# Select numeric columns excluding 'object' and 'int32'
numeric_cols = df.select_dtypes(exclude=['object', 'int32']).columns# defining the decide measurement
plt.decide(figsize=(25, 15))
# making for loop for subplots
for column in fluctuate(len(numeric_cols)):
plt.subplot(4, 4, column+1)
# plotting boxplot
sns.boxplot(y=df[numeric_cols[column]])
# defining column title for as title for each boxplot
plt.title(f'The boxplot of {numeric_cols[column]}')
# adjusting the spacing between subplots
plt.tight_layout()
plt.current()
# Convert columns to numeric, forcing errors to NaN
for i in col:
df[i] = pd.to_numeric(df[i], errors='coerce')# Itemizing of columns which have outliers
col = ['MinTemp','MaxTemp', 'Rainfall', 'WindGustSpeed', 'WindSpeed9am', 'WindSpeed3pm', 'Humidity9am', 'Pressure3pm', 'Pressure9am', 'Temp9am', 'Temp3pm']
# For loop for altering outliers
for i in col:
# Uncover Q1 and Q3
q1 = df[i].quantile(0.25)
q3 = df[i].quantile(0.75)
# Uncover IQR
iqr = q3 - q1
# Uncover lower and better limits
lower_limit = q1 - 1.5 * iqr
upper_limit = q3 + 1.5 * iqr
# Uncover median of the column
median = df[i].median()
# Alternate outliers with median
df[i] = np.the place((df[i] < lower_limit) | (df[i] > upper_limit), median, df[i])
Dari gambar terlihat bahwa outlier pada tiap variabel sudah berkurang, meskipun masih terdapat outlier pada variabel Rainfall, WindGustSpeed,Humidity9am,Presure9am, dan Presure3pm. Akan tetapi hal tersebut diabaikan karena outlier pada variabel tersebut memiliki jumlah yang sedikit sehingga tidak terlalu berpengaruh signifikan.
#INBALANCE DATA (OVERSAMPLING)
# checking the value counts of `RainTomorrow`
df['RainTomorrow'].value_counts()
# checking the rely plot of distinctive values of `RainTomorrow`
df['RainTomorrow'].value_counts().plot(kind='bar')
# establishing the title
plt.title('Bar Plot of price counts of RainTomorrow Sooner than Oversampling')
# rotating the x axis labels
plt.xticks(rotation=360)
plt.xlabel({0: 'No rain ', 1:'Rain'})
plt.current()#PENANGANAN
# definig the X and y
X_resample = df.drop('RainTomorrow' , axis=1)
y_resample = df['RainTomorrow']
# splitting the information into apply and verify
X_train_resample , X_test_resample , y_train_resample , y_test_resample = train_test_split(X_resample , y_resample , test_size=0.2 , random_state=42)
# calling SMOTE
smote = SMOTE(random_state=42)
# making use of SMOTE on teaching data
X_train_resample , y_train_resample = smote.fit_resample(X_train_resample , y_train_resample)
#CEK KORELASI
# Heatmap of correlation matrix of numeric choices in addition to `day, month & yr`# calculating the correlation matrix
corr_matrix = df.select_dtypes(embody='float64').corr()
# defining the decide measurement
plt.decide(figsize=(16,6))
# plotting the heatmap
sns.heatmap(corr_matrix , cbar=False , cmap='viridis' , annot=True , fmt='.2f' , linewidths=0.5, linecolor='black')
# rotating the x axis labels
plt.xticks(rotation=45)
# establishing the title
plt.title('Correlation Matrix of Numeric Choices')
plt.current()
4. DEFINE FEATURE AND TARGET
Langkah selanjutnya adalah membagi data ke dalam data apply dan data verify. Akan tetapi sebelum membagi menjadi data verify dan data apply terlebih dahulu hal yang harus dilakukan adalah melakukan defining choices. Hal ini bertujuan untuk mencegah adanya overfiting dan mengurangi adanya multikolinieritas. Dengan cara melakukan drop variabel dari choices yang akan kita gunakan, yaitu variabel yang memiliki nilai VIF tinggi. Berikut adalah nilai VIF dari tiap variabel :
variabel yang akan didrop dari choices yang akan digunakan adalah variabel Temp3pm,Temp9am, dan Pressure3pm. Pada tabel 6 terlihat bahwa nilai VIF untuk variabel MinTemp sebesar 42,40 akan tetapi variabel tersebut tidak dilakukan drop variabel karena variabel MaxTemp memiliki peran yang penting pada saat dilakukan analisis. Setelah dilakukan defining choices maka dilakukan pembagian data apply dan data verify dengan perbandingan data apply sebesar 80% dan data verify sebesar 20%.
5. KLASIFIKASI
a. Regresi Logistik
#apply verify reduce up
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=42)
# calling the logistic regression
model = LogisticRegression()# making use of logistic regression
model.match(X_train, y_train)
# predicting values
y_pred = model.predict(X_test)
# checking accuracy score
print('Accuracy Score :', accuracy_score(y_test, y_pred) , 'n')
# checking recall score
print('Recall Score :',recall_score(y_test, y_pred) , 'n')
# checking precision score
print('Precision Score :',precision_score(y_test, y_pred) , 'n')
# checking f1 score
print('F1 Score :',f1_score(y_test, y_pred) , 'n')
# checking classification report
print('Classification Report :', 'n',classification_report(y_test, y_pred))
# confusion matrix heatmap
sns.heatmap(confusion_matrix(y_test, y_pred) , annot=True , fmt='.2f' , xticklabels=['True Negatif' , 'True Positive'] ,
yticklabels=['True Negatif' , 'True Positive'] , cbar=False)# establishing the x and y label
plt.xlabel('Exact')
plt.ylabel('Predicted')
# establishing the title
plt.title('Confusion Matrix of Logistic Regression')
plt.current()
b. Random Forest
from sklearn.ensemble import RandomForestClassifier
from sklearn.metrics import accuracy_score, recall_score, precision_score, f1_score, classification_report
from sklearn.tree import export_graphviz
import graphviz
import pydotplus
from IPython.present import Image# Calling the random forest
rf = RandomForestClassifier(random_state=42)
# Making use of random forest
rf.match(X_train, y_train)
# predicting values
y_pred = rf.predict(X_test)
# checking accuracy score
print('Accuracy Score :', accuracy_score(y_test, y_pred) , 'n')
# checking recall score
print('Recall Score :',recall_score(y_test, y_pred) , 'n')
# checking precision score
print('Precision Score :',precision_score(y_test, y_pred) , 'n')
# checking f1 score
print('F1 Score :',f1_score(y_test, y_pred) , 'n')
# checking classification report
print('Classification Report :', 'n',classification_report(y_test, y_pred))
# confusion matrix heatmap
sns.heatmap(confusion_matrix(y_test, y_pred) , annot=True , fmt='.2f' , xticklabels=['True Negative' , 'True Positive'] ,
yticklabels=['True Negative' , 'True Positive'] , cbar=False)# establishing the x and y label
plt.xlabel('Exact')
plt.ylabel('Predicted')
# establishing the title
plt.title('Confusion Matrix of Random Forest Classifier')
plt.current()
Cek akurasi data teaching & testing
# calculating the apply accuracy
y_pred_train = rf.predict(X_train)
print(accuracy_score(y_train, y_pred_train))# calculating the verify accuracy
y_pred_test = rf.predict(X_test)
print(accuracy_score(y_test, y_pred_test))
Karena terindikasi over changing into, maka dilakukan Hypertunning Parameter
# calling the random forest and adjusting the parameters
model = RandomForestClassifier(
n_estimators=150, # Number of bushes
max_depth=10, # Most depth of each tree
min_samples_split=10, # Minimal samples required to separate an interior node
min_samples_leaf=5, # Minimal samples required to be at a leaf node
max_features=5, # Number of choices to consider when looking for the easiest reduce up
criterion='entropy', # Splitting criterion
random_state=42
)# changing into the model
model.match(X_train, y_train)
# calculating the apply and verify accuracy
y_pred_train = model.predict(X_train)
y_pred_test = model.predict(X_test)
# printing the apply and verify accuracy
print(f"Put together accuracy: {accuracy_score(y_train, y_pred_train)}")
print(f"Verify accuracy: {accuracy_score(y_test, y_pred_test)}")
c. Extreme Gradient Boosting (XGBoost)
# calling the xgboost classifier
xgb = XGBClassifier(random_state=42)
# changing into the model
xgb.match(X_train, y_train)# predicting values
y_pred = xgb.predict(X_test)
# checking accuracy score
print('Accuracy Score :', accuracy_score(y_test, y_pred) , 'n')
# checking recall score
print('Recall Score :',recall_score(y_test, y_pred) , 'n')
# checking precision score
print('Precision Score :',precision_score(y_test, y_pred) , 'n')
# checking f1 score
print('F1 Score :',f1_score(y_test, y_pred) , 'n')
# checking classification report
print('Classification Report :', 'n',classification_report(y_test, y_pred))
# confusion matrix heatmap
# confusion matrix heatmap
sns.heatmap(confusion_matrix(y_test, y_pred) , annot=True , fmt='.2f' , xticklabels=['True Negative' , 'True Positive'] ,
yticklabels=['True Negative' , 'True Positive'] , cbar=False)plt.title('Confusion Matrix of XGBoost Classifier')
plt.current()
d. Dedication Tree
from sklearn.tree import DecisionTreeClassifier# Calling the Dedication Tree classifier
dt = DecisionTreeClassifier(random_state=42)
# Changing into the model
dt.match(X_train, y_train)
# Predicting values
y_pred = dt.predict(X_test)
#Checking accuracy score
print('Accuracy Score :', accuracy_score(y_test, y_pred), 'n')
# Checking recall score
print('Recall Score :', recall_score(y_test, y_pred), 'n')
# Checking precision score
print('Precision Score :', precision_score(y_test, y_pred), 'n')
# Checking f1 score
print('F1 Score :', f1_score(y_test, y_pred), 'n')
# Checking classification report
print('Classification Report :', 'n', classification_report(y_test, y_pred))
# Confusion matrix heatmap
sns.heatmap(confusion_matrix(y_test, y_pred), annot=True, fmt='.2f',
xticklabels=['True Negative', 'True Positive'],
yticklabels=['True Negative', 'True Positive'], cbar=False)
plt.title('Confusion Matrix of Dedication Tree Classifier')
plt.current()
e. Perbandingan Keseluruhan Metode
# Importing essential libraries for the fashions
from sklearn.linear_model import LogisticRegression
from sklearn.ensemble import RandomForestClassifier
from sklearn.tree import DecisionTreeClassifier
from xgboost import XGBClassifier# Creating an empty itemizing to retailer outcomes
final result = []
# Making a dictionary of fashions
fashions = {
'Logistic Regression': LogisticRegression(random_state=42),
'Random Forest': RandomForestClassifier(random_state=42),
'XGBoost': XGBClassifier(random_state=42),
'Dedication Tree': DecisionTreeClassifier(random_state=42)
}
# Changing into the model and evaluating effectivity
for title, model in fashions.objects():
# Timing the match course of
start_fit = time.time()
# Changing into the model
model.match(X_train, y_train)
# Ending time of the match course of
end_fit = time.time()
# Calculating the match time for each model
fit_time = end_fit - start_fit
# Taking predictions from model on verify data
y_pred = model.predict(X_test)
# Calculating the accuracy score
acc = accuracy_score(y_test, y_pred)
# Calculating the precision score
precision = precision_score(y_test, y_pred)
# Calculating the recall score
recall = recall_score(y_test, y_pred)
# Appending the result inside the itemizing
final result.append((title, acc, precision, recall, fit_time))
# Printing the evaluation outcomes of every model
result_df = pd.DataFrame(final result, columns=['Model', 'Accuracy Score', 'Precision', 'Recall', 'Fit Time (s)'])
print(result_df)
Dari tabel dapat dilihat bahwa :
· Model dengan akurasi tertinggi adalah XGBoost (0.898411).
· Model dengan presisi tertinggi adalah XGBoost (0.916866).
· Model dengan recall tertinggi adalah Random Forest (0.873350), tetapi XGBoost juga memiliki nilai recall yang sangat baik (0.859569).
· Model dengan waktu latih tercepat adalah XGBoost (1.708394 detik).
import matplotlib.pyplot as plt# Info
fashions = ['Logistic Regression', 'Random Forest', 'XGBoost', 'Decision Tree']
accuracy = [0.769956, 0.889137, 0.898411, 0.822644]
f1_score = [0.748807, 0.879451, 0.887053, 0.809980]
# Barchart Akurasi
plt.decide(figsize=(10, 6))
bars = plt.bar(fashions, accuracy, shade=['blue', 'green', 'red', 'purple'])
plt.xlabel('Model')
plt.ylabel('Akurasi')
plt.title('Perbandingan Akurasi Antar Model')
plt.ylim(0, 1)
# Menambahkan angka persentase di atas bar
for bar in bars:
yval = bar.get_height()
plt.textual content material(bar.get_x() + bar.get_width()/2, yval, f'{yval*100:.2f}%', ha='coronary heart', va='bottom')
plt.current()
# Barchart F1 Score
plt.decide(figsize=(10, 6))
bars = plt.bar(fashions, f1_score, shade=['blue', 'green', 'red', 'purple'])
plt.xlabel('Model')
plt.ylabel('F1 Score')
plt.title('Perbandingan F1 Score Antar Model')
plt.ylim(0, 1)
# Menambahkan angka persentase di atas bar
for bar in bars:
yval = bar.get_height()
plt.textual content material(bar.get_x() + bar.get_width()/2, yval, f'{yval*100:.2f}%', ha='coronary heart', va='bottom')
plt.current()
6. KESIMPULAN
Berdasarkan penelitian yang dilakukan untuk menentukan metode klasifikasi terbaik dalam memprediksi hujan Australia menggunakan dataset “Rain in Australia”, diperoleh hasil evaluasi dari empat model klasifikasi yaitu Logistic Regression, Random Forest, Extreme Gradient Boosting (XGBoost), dan Dedication Tree. Analisis ini menunjukkan bahwa model XGBoost memberikan performa terbaik dengan akurasi tertinggi sebesar 89.8 % dan F1 Score tertinggi sebesar 88.73 %. Selain itu, XGBoost juga menunjukkan waktu pemrosesan yang paling efisien yaitu 1.71 detik.
Sehingga dapat disimpulkan bahwa XGBoost adalah model terbaik untuk digunakan dalam memprediksi hujan di hari esok di Australia. Model ini tidak hanya memberikan hasil yang sangat akurat tetapi juga efisien dalam waktu pemrosesan. Oleh karena itu, disarankan untuk menggunakan XGBoost sebagai model utama untuk klasifikasi ini. Selain itu, meskipun XGBoost sudah menunjukkan performa terbaik, optimasi lebih lanjut terhadap hyperparameter model dapat dilakukan untuk memastikan bahwa model mencapai performa maksimal. Evaluasi berkelanjutan dengan dataset yang lebih besar dan lebih bervariasi juga perlu dilakukan untuk memastikan model tetap sturdy dan dapat diandalkan dalam berbagai kondisi.