Pengatar Data Science
~ Tugas 3 ~
| Kontak | : \(\downarrow\) |
| mugemisausan05@gmail.com | |
| https://www.instagram.com/saram.05/ | |
| RPubs | https://rpubs.com/sausanramadhani/ |
Bab 5 klasifikasi I : Percobaan dan Prediksi
5.1 Ringkasan
Pada bab sebelumnya, lebih terfokus pada pertanyaan-pertanyaan mengenai data analisis deskriptif dan eksploratif. Bab kali ini dan seterusnya merupakan upaya pertama dalam menjawab pertanyaan prediktif mengenai suatu data. Khususnya, kita lebih fokus pada klasifikasi yang mana menggunakan satu atau lebih variabel untuk memprediksi nilai variabel kategori yang diminati. Bab ini akan membahas tentang dasar-dasar klasifikasi, bagaimana langkah sebelum memproses data supaya menjadi sesuai untuk digunakan dalam suatu pengklasifikasi, dan bagaimana untuk menggunakan data observasi untuk membuat prediksi. Pada bab selanjutnya akan fokus pada bagaimana mengevaluasi seberapa akurat prediksi tersebut dari klasifikasi yang kita buat, juga bagaimana untuk meningkatkan klasifikasi kita (jika memungkinkan) untuk memaksimalkan akurasinya.
5.2 Tujuan Pembelajaran
Di akhir bab, pembaca akan bisa melakukan hal berikut ini :
• Mengenali situasi di mana pengklasifikasi dapat sesuai untuk membuat prediksi.
• Menjelaskan apa itu data set pelatihan dan bagaimana ini digunakan untuk klasifikasi.
• Menafsirkan output dari pengklasifikasi.
• Menghitung menggunakan tangan, jarak garis lurus antar poin pada grafik saat terdapat dua variabel prediktor.
• Menjelaskan klasifikasi algoritma K-lingkup terdekat.
• Melakukan klasifikasi K-lingkup terdekat di R menggunakan tidymodels.
• Menggunakan recipe untuk praproses data supaya lebih terpusat, berskala, dan seimbang.
• Menggabungkan prapemrosesan dan pelatihan model menggunakan workflow.
5.3 Permasalahan Klasifikasi
klasifikasi dapat memprediksi kelas kategorikal (terkadang disebut juga label) untuk pengamatan yang diberikan ialah variabel lain (terkadang disebut juga features). Biasanya, pengklasifikasi menetapkan suatu observasi yang tanpa diketahui kelasnya menjadi sebuah kelas. Observasi ini dengan diketahui kelasnya yang kita gunakan sebagai dasar prediksi disebut juga training set. Nama ini berawal dari fakta bahwa kita menggunakan data untuk membuat prediksi pada data baru yang kita tidak ketahui kelasnya. Terdapat banyak kemungkinan metode yang bisa digunakan untuk memprediksi kelas atau label kategori untuk suatu observasi.
5.4 Eksplorasi Data Set
Terdapat data set mengenai kanker payudara dan seperti analisis data pada umumnya maka kita merumuskan pertanyaan (rumusan masalah) yang tepat bahwa kita ingin menjawabnya. Menggunakan pengukuran data tumor yang di dalamnya berisi diagnosis jinak atau ganas dan parameter lainnya seperti nukleostekstur (inti sel), perimeter area dan lain-lain. Setelah kita mengetahui data tersebut dengan beberapa pertanyaan yang berhubungan dengan data set.
5.4.1 Memuat data kanker
Kita menggunakan library tidyverse untuk mengakses datanya supaya lebih mudah dijalankan saat eksplor data dengan visualisasi.
library(tidyverse)Data yang akan di import berupa csv, maka kita harus memanggil data tersebut dengan menggunakan kode berikut ini :
getwd()## [1] "C:/Users/Lenovo/Documents/DOK. SAUSAN/Matana University/Semester 2/Pengantar Data Science"
dakan <- read.csv("wdbc.txt")
dakan5.4.2 Mendeskripsikan variabel-variabel dalam data set kanker
Tumor payudara itu bisa di diagnosa disebabkannya karena biopsy. Kemudian, prosesnya di buang dari badan dan diperiksa lagi apakah penyakit itu ada. Jika menggunakan metode tradisional memakan biaya cukup mahal dan jika memakai metode modern akan membutuhkan banyak pertimbangan dan perhitungan. Contohnya kita harus mengcolab data set, mengekstrak tissu yang jumlahnya sedikit dan inasive rendah.
Dari data set kanker, kita memiliki beberapa variabel sebagai berikut :
• ID: nomor identifikasi
• Class: diagnosis (M = ganas atau B = jinak)
• radius: rata-rata jarak dari pusat ke titik-titik pada keliling
• Tekstur: standar deviasi nilai skala abu-abu
• Perimeter: panjang kontur sekitarnya
• Area: area di dalam kontur
• Kehalusan/smoothness: variasi lokal dalam panjang radius
• compactness: rasio keliling kuadrat dan luas
• concavity: tingkat keparahan bagian cekung dari kontur
• concave points: jumlah bagian cekung dari kontur
• Simetri: seberapa mirip inti ketika dicerminkan
• Fraktal dimensi: pengukuran seberapa “kasar” kelilingnya
glimpse(dakan) # menampilkan nama variabel, tipe variabel, dan beberapa baris pertama dari data## Rows: 569
## Columns: 12
## $ ID <int> 842302, 842517, 84300903, 84348301, 84358402, 843786~
## $ Class <chr> "M", "M", "M", "M", "M", "M", "M", "M", "M", "M", "M~
## $ Radius <dbl> 1.0960995, 1.8282120, 1.5784992, -0.7682333, 1.74875~
## $ Texture <dbl> -2.0715123, -0.3533215, 0.4557859, 0.2535091, -1.150~
## $ Perimeter <dbl> 1.26881726, 1.68447255, 1.56512598, -0.59216612, 1.7~
## $ Area <dbl> 0.98350952, 1.90703027, 1.55751319, -0.76379174, 1.8~
## $ Smoothness <dbl> 1.56708746, -0.82623545, 0.94138212, 3.28066684, 0.2~
## $ Compactness <dbl> 3.28062806, -0.48664348, 1.05199990, 3.39991742, 0.5~
## $ Concavity <dbl> 2.65054179, -0.02382489, 1.36227979, 1.91421287, 1.3~
## $ Concave_Points <dbl> 2.53024886, 0.54766227, 2.03543978, 1.45043113, 1.42~
## $ Symmetry <dbl> 2.215565542, 0.001391139, 0.938858720, 2.864862154, ~
## $ Fractal_Dimension <dbl> 2.25376381, -0.86788881, -0.39765801, 4.90660199, -0~
Dari hasil diatas, kita dapat simpulkan bahwa class bertipe karakter. Karena kita akan bekerja dengan class sebagai variabel statistik kategorikal maka kita akan mengubahnya menjadi faktor menggunakan fungsi as_factor.
dakan <- dakan |>
mutate(Class = as.factor(Class))
glimpse(dakan)## Rows: 569
## Columns: 12
## $ ID <int> 842302, 842517, 84300903, 84348301, 84358402, 843786~
## $ Class <fct> M, M, M, M, M, M, M, M, M, M, M, M, M, M, M, M, M, M~
## $ Radius <dbl> 1.0960995, 1.8282120, 1.5784992, -0.7682333, 1.74875~
## $ Texture <dbl> -2.0715123, -0.3533215, 0.4557859, 0.2535091, -1.150~
## $ Perimeter <dbl> 1.26881726, 1.68447255, 1.56512598, -0.59216612, 1.7~
## $ Area <dbl> 0.98350952, 1.90703027, 1.55751319, -0.76379174, 1.8~
## $ Smoothness <dbl> 1.56708746, -0.82623545, 0.94138212, 3.28066684, 0.2~
## $ Compactness <dbl> 3.28062806, -0.48664348, 1.05199990, 3.39991742, 0.5~
## $ Concavity <dbl> 2.65054179, -0.02382489, 1.36227979, 1.91421287, 1.3~
## $ Concave_Points <dbl> 2.53024886, 0.54766227, 2.03543978, 1.45043113, 1.42~
## $ Symmetry <dbl> 2.215565542, 0.001391139, 0.938858720, 2.864862154, ~
## $ Fractal_Dimension <dbl> 2.25376381, -0.86788881, -0.39765801, 4.90660199, -0~
Kita bisa memverifikasikan level dari kolom Class menggunakan fungsi levels.
dakan |>
pull(Class) |>
levels()## [1] "B" "M"
5.4.3 Mengeksplor data kanker
Sebelum melakukan berbagai pemodelan, kita explore dulu data setnya. Kita pakai group_by, summarize, dan n untuk mencari jumlah dan persentase dari pengamatan tumor jinak dan ganas yang ada dalam data. Fungsi n bersamaan summarize saat disatukan dengan group_by bisa menghitung jumlah pengamatan di setiap kelompok kelas. Lalu kita hitung persentase tiap kelompok dengan membagi jumlah total pengamatan. Data kita mempunyai 357 (63%) jinak dan 212 (37%) ganas.
num_obs <- nrow(dakan)
dakan |>
group_by(Class) |>
summarize(
count = n(),
percentage = n() / num_obs*100
)Setelah itu, kita membuat plotnya yang mana melibatkan Perimeter dan Concavity. Selanjutnya, mari kita gambar alur yang menyebar untuk memvisualisasikan hubungan antara perimeter dan variabel yang menyempit. Alih-alih menggunakan palet standar ggplot, kita memilih warna kita sendiri —“orange2” untuk oranye terang dan “steelblue2” untuk biru terang — dan melewati mereka sebagai argumen nilai ke fungsi scale_color_manual. Kami juga membuat label kategori (” B “dan” M “) lebih mudah dibaca dengan mengubahnya menjadi”jinak (benign)” dan “ganas (maligant)” dengan menggunakan argumen label.
perim_concav <- dakan |>
ggplot(aes(x = Perimeter, y = Concavity, color = Class)) +
geom_point(alpha = 0.6) +
labs(x = "Perimeter (standardized)",
y = "Concavity (standardized)",
color = "Diagnosis") +
scale_color_manual(labels = c("Malignant", "Benign"),
values = c("orange2", "steelblue2")) +
theme(text = element_text(size = 12))
perim_concav5.5 Klasifikasi Menggunakan K-Nearest Neighbors
Terdapat beberapa cara untuk mengklasifikasikan data dengan menggunakan KNN (K-Nearest Neighbor) sebagai berikut :
5.5.1 Jarak antar poin
Kita bisa menghitung jarak antar poin dengan menggunakan K-Nearest Neighbors. Berikut ini kode perhitungannya :
new_obs_Perimeter <- 0
new_obs_Concavity <- 3.5 # nilai K terkecil
dakan |>
select(ID, Perimeter, Concavity, Class) |>
mutate(dist_from_new = sqrt((Perimeter - new_obs_Perimeter)^2 +
(Concavity - new_obs_Concavity)^2)) |>
arrange(dist_from_new) |>
slice(1:5) # 5 baris pertama5.5.2 Lebih dari dua penjelasan variabel
Untuk variabel yang lebih dari dua bisa menggunakan kode berikut ini :
new_obs_Perimeter <- 0
new_obs_Concavity <- 3.5
new_obs_Symmetry <- 1
dakan |>
select(ID, Perimeter, Concavity, Symmetry, Class) |>
mutate(dist_from_new = sqrt((Perimeter - new_obs_Perimeter)^2 +
(Concavity - new_obs_Concavity)^2 +
(Symmetry - new_obs_Symmetry)^2)) |>
arrange(dist_from_new) |>
slice(1:5) #5 baris pertama5.5.3 Penjumlahan Algoritma K-Nearest Neighbors
Untuk mengklasifikasi pengamatan baru menggunakan KNN, kita bisa melakukan tahapan berikut :
• Menghitung jarak antara pengamatan baru dan setiap pengamatan dalam set pelatihan.
• Mengurutkan tabel data dalam urutan menaik menurut jarak.
• Pilih baris KNN teratas dari tabel yang diurutkan.
• Klasifikasikan pengamatan baru berdasarkan suara mayoritas dari kelas tetangga.
5.6 K-nearest neighbors menggunakan tidymodels
Kita menggunakan fungsi select untuk memilih kolom data yang akan difokuskan saat memproses K-Nearest Neighbors. Berikut ini kode KNN menggunakan tidymodels :
library(tidymodels)
kanker_train <- dakan |>
select(Class, Perimeter, Concavity)
kanker_trainUntuk pemodelan dari K-Nearest Neighbors bisa menggunakan fungsi nearest_neighbor (K=5). Kita juga menggunakan fungsi set_engine untuk menentukan jenis metode/model yang akan digunakan. Fungsi set_mode untuk menentukan klasifikasi K-Nearest Neighbors. Berikut ini kodenya :
knn_spec <- nearest_neighbor(weight_func = "rectangular", neighbors = 5) |>
set_engine("kknn") |>
set_mode("classification")
knn_spec## K-Nearest Neighbor Model Specification (classification)
##
## Main Arguments:
## neighbors = 5
## weight_func = rectangular
##
## Computational engine: kknn
Untuk menyesuaikan model pada data kanker payudara, kita harus melewati spesifikasi model dan kumpulan data ke fungsi fit. Kita juga perlu menentukan variabel apa yang akan digunakan sebagai prediktor dan variabel apa yang akan digunakan sebagai target. Di bawah, argumen Class ~ Perimeter + Concavity menetapkan bahwa Class adalah variabel target (yang ingin kita prediksi), dan Perimeter dan Concavity akan digunakan sebagai prediktor.
knn_fit <- knn_spec |>
fit(Class ~ Perimeter + Concavity, data = kanker_train)knn_fit <- knn_spec |>
fit(Class ~ ., data = kanker_train)
knn_fit## parsnip model object
##
## Fit time: 51ms
##
## Call:
## kknn::train.kknn(formula = Class ~ ., data = data, ks = min_rows(5, data, 5), kernel = ~"rectangular")
##
## Type of response variable: nominal
## Minimal misclassification: 0.07557118
## Best kernel: rectangular
## Best k: 5
new_obs <- tibble(Perimeter = 0, Concavity = 3.5)
predict(knn_fit, new_obs)5.7 Memproses Data Menggunakan tidymodels
5.7.1 Pemusatan dan Penskalaan
Memproses data menggunakan tidymodels berawal dari data unscaled_kanker melakukan perubahan tipe data menjadi faktor dan melakukan pemilihan data diantaranta Class, Area, Smoothness saat pemrosesan menggunakan fungsi select.
unscaled_kanker <- read_csv("unscaled_wdbc.txt") |>
mutate(class = as_factor(Class)) |>
select(Class, Area, Smoothness)
unscaled_kankeruc_recipe <- recipe(Class ~ ., data = unscaled_kanker)
print(uc_recipe)## Recipe
##
## Inputs:
##
## role #variables
## outcome 1
## predictor 2
uc_recipe <- uc_recipe |>
step_scale(all_predictors()) |>
step_center(all_predictors()) |>
prep()
uc_recipe## Recipe
##
## Inputs:
##
## role #variables
## outcome 1
## predictor 2
##
## Training data contained 569 data points and no missing data.
##
## Operations:
##
## Scaling for Area, Smoothness [trained]
## Centering for Area, Smoothness [trained]
scaled_cancer <- bake(uc_recipe, unscaled_kanker)
scaled_cancer5.7.2 Pengimbangan
Permasalahan ketidakseimbangan data, misalnya seperti mengambil 3 data dari ganas (malignant) dan menyimpan semua data Benign dengan menggunakan fungsi slice_head().
rare_cancer <- bind_rows(
filter(dakan, Class == "B"),
dakan |> filter(Class == "M") |> slice_head(n=3)
) |>
select(Class, Perimeter, Concavity)
rare_plot <- rare_cancer |>
ggplot(aes(x = Perimeter, y = Concavity, color = Class)) +
geom_point(alpha = 0.5) +
labs(x = "Perimeter (standardized)",
y = "Concavity (standardized)",
color = "Diagnosis") +
scale_color_manual(labels = c("Malignant", "Benign"),
values = c("orange2", "steelblue2")) +
theme(text = element_text(size = 12))
rare_plotUntuk menghindari permasalahan di atas, maka kita melakukan cara statistika yaitu dengan menambahkan oversampling pada data ups_recipe dan menggunakan fungsi step_upsample() dari package themis.
library(themis)
ups_recipe <- recipe(Class ~ ., data = rare_cancer) |>
step_upsample(Class, over_ratio = 1, skip = FALSE) |>
prep()
ups_recipe## Recipe
##
## Inputs:
##
## role #variables
## outcome 1
## predictor 2
##
## Training data contained 360 data points and no missing data.
##
## Operations:
##
## Up-sampling based on Class [trained]
Untuk melihat apakah proses Balancing data sudah sukses kita dapat menggunakan metode dibawah ini.
upsampled_cancer <- bake(ups_recipe, rare_cancer)
upsampled_cancer |>
group_by(Class) |>
summarize(n = n())5.8 Menyatukannya Dalam Sebuah Workflow
Koleksi package tidymodels juga menyediakan workflow, cara untuk menyatukan beberapa langkah analisis data tanpa banyak kode yang diperlukan untuk langkah perantara. Untuk mengilustrasikan keseluruhan pipeline, mari kita mulai dari awal dengan data unscaled_wdbc.csv. Pertama kita akan memuat data, membuat model, dan menentukan resep bagaimana data harus diproses sebelumnya:
# load the unscaled cancer data
# and make sure the target Class variable is a factor
unscaled_kanker <- read.csv("unscaled_wdbc.txt") |>
mutate(Class = as_factor(Class))
# create the KNN model
knn_spec <- nearest_neighbor(weight_func = "rectangular", neighbors = 7) |>
set_engine("kknn") |>
set_mode("classification")
# create the centering / scaling recipe
uc_recipe <- recipe(Class ~ Area + Smoothness, data = unscaled_kanker) |>
step_scale(all_predictors()) |>
step_center(all_predictors())Kita tidak menggunakan fungsi select untuk mengekstrak variabel yang relevan dari data frame.
knn_fit <- workflow() |>
add_recipe(uc_recipe) |>
add_model(knn_spec) |>
fit(data = unscaled_kanker)
knn_fit## == Workflow [trained] ==========================================================
## Preprocessor: Recipe
## Model: nearest_neighbor()
##
## -- Preprocessor ----------------------------------------------------------------
## 2 Recipe Steps
##
## * step_scale()
## * step_center()
##
## -- Model -----------------------------------------------------------------------
##
## Call:
## kknn::train.kknn(formula = ..y ~ ., data = data, ks = min_rows(7, data, 5), kernel = ~"rectangular")
##
## Type of response variable: nominal
## Minimal misclassification: 0.112478
## Best kernel: rectangular
## Best k: 7
Untuk melakukan prediksi pada penelitian kita gunakan predict() dengan objeknya adalah knn_fit. Dibawah ini kita lakukan prediksi pada data Class dengan dua label penelitian yang berbeda yaitu dengan Area 1 = 500, Area 2 = 1500, Smoothness 1 = 0.075 dan Smoothness 2 = 0.1 :
new_observation <- tibble(Area = c(500, 1500), Smoothness = c(0.075, 0.1))
prediction <- predict(knn_fit, new_observation)
prediction# create the grid of area/smoothness vals, and arrange in a data frame
are_grid <- seq(min(unscaled_kanker$Area),
max(unscaled_kanker$Area),
length.out = 100)
smo_grid <- seq(min(unscaled_kanker$Smoothness),
max(unscaled_kanker$Smoothness),
length.out = 100)
asgrid <- as_tibble(expand.grid(Area = are_grid,
Smoothness = smo_grid))
# use the fit workflow to make prediction at the grid points
knnPredGrid <- predict(knn_fit, asgrid)
#bind the predictions as a new column with the grid points
prediction_table <- bind_cols(knnPredGrid, asgrid) |>
rename(Class = .pred_class)
# plot:
# 1. the colored scatter of the original data
# 2. the faded colored scatter for the grid points
wkflw_plot <-
ggplot() +
geom_point(data = unscaled_kanker,
mapping = aes(x = Area,
y = Smoothness,
color = Class),
alpha = 0.75) +
geom_point(data = prediction_table,
mapping = aes(x = Area,
y = Smoothness,
color = Class),
alpha = 0.02,
size = 5) +
labs(color = "Diagnosis",
x = "Area (standardized)",
y = "Smoothness (standardized)") +
scale_color_manual(labels = c("Malignant", "Benign"),
values = c("orange2", "steelblue2")) +
theme(text = element_text(size = 12))
wkflw_plotBerdasarkan plot diatas, pada area 1000 sampai 1500 dengan kehalusan antara 0.075 sampai 0.125 merupakan titik kumpul terbanyak dari tumor ganas. Sedangkan, pada area 500 dengan kehalusan 0.075 sampai 0.100 merupakan titik kumpul terbanyak dari tumor jinak.