Impor dataset

library(readxl)
df <- read_excel("~/Desktop/Dataset 17_Dataset Kesiapan Nakes Indonesia.xlsx")
glimpse(df)
## Rows: 210
## Columns: 15
## $ No.                  <dbl> 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15…
## $ Usia                 <dbl> 42, 36, 37, 49, 42, 61, 53, 42, 37, 46, 43, 60, 3…
## $ `Pengalaman bekerja` <chr> "6-10 tahun", "6-10 tahun", "11-20 tahun", "11-20…
## $ Pendidikan           <chr> "SMP/SMA", NA, "SMP/SMA", "SMP/SMA", "SMP/SMA", "…
## $ Pekerjaan            <chr> "CHW", "CHW", "CHW", "CHW", "CHW", "CHW", NA, "CH…
## $ `Keahlian Komputer`  <chr> "Terbatas", "Terbatas", "Terbatas", "Bagus", "Bag…
## $ `Fasilitas Android`  <chr> "Ada", "Ada", "Ada", "Ada", "Ada", "Ada", "Ada", …
## $ `Aplikasi di HP`     <chr> "Tidak Ada", "Ada", "Ada", "Ada", "Ada", "Ada", "…
## $ `Pengalaman HIS`     <chr> "Tidak", "Ya", "Tidak", "Ya", "Ya", "Tidak", "Ya"…
## $ `Akses Internet`     <chr> "Tidak", "Ya", "Tidak", "Tidak", "Tidak", "Tidak"…
## $ `Anggaran Bulanan`   <chr> "Ya", "Ya", "Ya", "Ya", "Tidak", "Tidak", "Ya", "…
## $ `Kerja Kolaborasi`   <chr> "Ya", "Ya", "Ya", "Ya", "Ya", "Ya", "Ya", "Ya", "…
## $ Kemauan              <chr> "Ya", "Ya", "Ya", "Ya", "Tidak", "Tidak", "Ya", "…
## $ `Skor Kesiapan`      <dbl> 3.95, 3.15, 3.75, 3.90, 3.45, 3.65, 3.95, 3.20, 3…
## $ `Kategori Kesiapan`  <chr> "Siap", "Tidak Siap", "Siap", "Siap", "Siap", "Si…

Skim dataset

df <- df %>% janitor::clean_names() #Merapikan nama atribut
glimpse(df)
## Rows: 210
## Columns: 15
## $ no                 <dbl> 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, …
## $ usia               <dbl> 42, 36, 37, 49, 42, 61, 53, 42, 37, 46, 43, 60, 36,…
## $ pengalaman_bekerja <chr> "6-10 tahun", "6-10 tahun", "11-20 tahun", "11-20 t…
## $ pendidikan         <chr> "SMP/SMA", NA, "SMP/SMA", "SMP/SMA", "SMP/SMA", "SM…
## $ pekerjaan          <chr> "CHW", "CHW", "CHW", "CHW", "CHW", "CHW", NA, "CHW"…
## $ keahlian_komputer  <chr> "Terbatas", "Terbatas", "Terbatas", "Bagus", "Bagus…
## $ fasilitas_android  <chr> "Ada", "Ada", "Ada", "Ada", "Ada", "Ada", "Ada", "A…
## $ aplikasi_di_hp     <chr> "Tidak Ada", "Ada", "Ada", "Ada", "Ada", "Ada", "Ad…
## $ pengalaman_his     <chr> "Tidak", "Ya", "Tidak", "Ya", "Ya", "Tidak", "Ya", …
## $ akses_internet     <chr> "Tidak", "Ya", "Tidak", "Tidak", "Tidak", "Tidak", …
## $ anggaran_bulanan   <chr> "Ya", "Ya", "Ya", "Ya", "Tidak", "Tidak", "Ya", "Ti…
## $ kerja_kolaborasi   <chr> "Ya", "Ya", "Ya", "Ya", "Ya", "Ya", "Ya", "Ya", "Ya…
## $ kemauan            <chr> "Ya", "Ya", "Ya", "Ya", "Tidak", "Tidak", "Ya", "Ya…
## $ skor_kesiapan      <dbl> 3.95, 3.15, 3.75, 3.90, 3.45, 3.65, 3.95, 3.20, 3.0…
## $ kategori_kesiapan  <chr> "Siap", "Tidak Siap", "Siap", "Siap", "Siap", "Siap…
df <- df %>% mutate_if(is.character, as.factor) %>% 
        select(-c(no, kategori_kesiapan)) %>% #Drop variabel yang tidak relevan
        mutate(usia = as.integer(usia),
               skor_kesiapan = as.integer(skor_kesiapan))

skimr::skim(df)
Data summary
Name df
Number of rows 210
Number of columns 13
_______________________
Column type frequency:
factor 11
numeric 2
________________________
Group variables None

Variable type: factor

skim_variable n_missing complete_rate ordered n_unique top_counts
pengalaman_bekerja 0 1 FALSE 4 6-1: 81, 11-: 58, kur: 45, leb: 26
pendidikan 1 1 FALSE 4 SMP: 120, Dip: 71, Sar: 16, pos: 2
pekerjaan 1 1 FALSE 2 CHW: 139, Mid: 70
keahlian_komputer 1 1 FALSE 2 Bag: 123, Ter: 86
fasilitas_android 0 1 FALSE 2 Ada: 207, Tid: 3
aplikasi_di_hp 1 1 FALSE 2 Ada: 189, Tid: 20
pengalaman_his 1 1 FALSE 2 Tid: 120, Ya: 89
akses_internet 0 1 FALSE 2 Tid: 157, Ya: 53
anggaran_bulanan 1 1 FALSE 2 Ya: 171, Tid: 38
kerja_kolaborasi 1 1 FALSE 2 Ya: 141, Tid: 68
kemauan 1 1 FALSE 2 Ya: 135, Tid: 74

Variable type: numeric

skim_variable n_missing complete_rate mean sd p0 p25 p50 p75 p100 hist
usia 0 1 42.4 10.27 22 35 42.5 50 64 ▅▃▇▆▃
skor_kesiapan 0 1 5.0 26.35 2 3 3.0 3 385 ▇▁▁▁▁
summary(df)
##       usia                pengalaman_bekerja    pendidikan    pekerjaan  
##  Min.   :22.0   11-20 tahun        :58       Diploma : 71   CHW    :139  
##  1st Qu.:35.0   6-10 tahun         :81       postgrad:  2   Midwife: 70  
##  Median :42.5   kurang dari 5 tahun:45       Sarjana : 16   NA's   :  1  
##  Mean   :42.4   lebih dari 20 tahun:26       SMP/SMA :120                
##  3rd Qu.:50.0                                NA's    :  1                
##  Max.   :64.0                                                            
##  keahlian_komputer fasilitas_android   aplikasi_di_hp pengalaman_his
##  Bagus   :123      Ada      :207     Ada      :189    Tidak:120     
##  Terbatas: 86      Tidak Ada:  3     Tidak Ada: 20    Ya   : 89     
##  NA's    :  1                        NA's     :  1    NA's :  1     
##                                                                     
##                                                                     
##                                                                     
##  akses_internet anggaran_bulanan kerja_kolaborasi  kemauan    skor_kesiapan    
##  Tidak:157      Tidak: 38        Tidak: 68        Tidak: 74   Min.   :  2.000  
##  Ya   : 53      Ya   :171        Ya   :141        Ya   :135   1st Qu.:  3.000  
##                 NA's :  1        NA's :  1        NA's :  1   Median :  3.000  
##                                                               Mean   :  5.005  
##                                                               3rd Qu.:  3.000  
##                                                               Max.   :385.000

Diperoleh informasi bahwa terdapat missing data pada 8 variabel bertipe kategorik, yaitu pendidikan, pekerjaan, keahlian_komputer, aplikasi_di_hp, pengalaman_his, anggaran_bulanan, *kerja_kolaborasi, dan kemauan masing-masing berjumlah 1 missing values. Sedangkan variabel bertipe numerik, yaitu usia dan skor_kesiapan tidak memiliki missing values.

Pengecekan outlier

data_boxplot <- df %>% select_if(is.numeric) %>%
  reshape2::melt() 
## No id variables; using all as measure variables
data_boxplot %>% ggplot(aes(x=variable,y=value)) +
  geom_boxplot(fill = "white", colour = "#3366FF") + 
    facet_wrap(~variable,scales = "free")+ 
    labs(title = "Apakah terdapat outlier dalam data?")+
    ylab("") + xlab("")

> Bisa dikatakan bahwa pada variabel skor_kesiapan memiliki satu nilai outlier yang kemungkinan besar adalah suatu noise dalam datanya. Sehingga, pada tahap selanjutnya observasi tersebut dihapus.

Data Pre-processing

df_preproc <- df %>% dplyr::filter(skor_kesiapan <10) #Observasi dengan nilai skor_kesiapan >10 (noise) dihilangkan dari dataset.
imputasi <- compute(df_preproc, method = "median/mode")
df_preproc <- impute(df_preproc, object = imputasi) # melakukan imputasi

glimpse(df_preproc)
## Rows: 209
## Columns: 13
## $ usia               <int> 42, 36, 37, 49, 42, 61, 53, 42, 37, 46, 43, 60, 36,…
## $ pengalaman_bekerja <fct> 6-10 tahun, 6-10 tahun, 11-20 tahun, 11-20 tahun, 1…
## $ pendidikan         <fct> SMP/SMA, SMP/SMA, SMP/SMA, SMP/SMA, SMP/SMA, SMP/SM…
## $ pekerjaan          <fct> CHW, CHW, CHW, CHW, CHW, CHW, CHW, CHW, CHW, CHW, C…
## $ keahlian_komputer  <fct> Terbatas, Terbatas, Terbatas, Bagus, Bagus, Terbata…
## $ fasilitas_android  <fct> Ada, Ada, Ada, Ada, Ada, Ada, Ada, Ada, Ada, Ada, A…
## $ aplikasi_di_hp     <fct> Tidak Ada, Ada, Ada, Ada, Ada, Ada, Ada, Ada, Ada, …
## $ pengalaman_his     <fct> Tidak, Ya, Tidak, Ya, Ya, Tidak, Ya, Ya, Ya, Tidak,…
## $ akses_internet     <fct> Tidak, Ya, Tidak, Tidak, Tidak, Tidak, Tidak, Tidak…
## $ anggaran_bulanan   <fct> Ya, Ya, Ya, Ya, Tidak, Tidak, Ya, Tidak, Tidak, Ya,…
## $ kerja_kolaborasi   <fct> Ya, Ya, Ya, Ya, Ya, Ya, Ya, Ya, Ya, Ya, Ya, Ya, Ya,…
## $ kemauan            <fct> Ya, Ya, Ya, Ya, Tidak, Tidak, Ya, Ya, Ya, Ya, Ya, T…
## $ skor_kesiapan      <int> 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 2, 3, 3, 3, …
summary(df_preproc)
##       usia                 pengalaman_bekerja    pendidikan    pekerjaan  
##  Min.   :22.00   11-20 tahun        :57       Diploma : 70   CHW    :140  
##  1st Qu.:35.00   6-10 tahun         :81       postgrad:  2   Midwife: 69  
##  Median :43.00   kurang dari 5 tahun:45       Sarjana : 16                
##  Mean   :42.41   lebih dari 20 tahun:26       SMP/SMA :121                
##  3rd Qu.:50.00                                                            
##  Max.   :64.00                                                            
##  keahlian_komputer fasilitas_android   aplikasi_di_hp pengalaman_his
##  Bagus   :123      Ada      :206     Ada      :189    Tidak:120     
##  Terbatas: 86      Tidak Ada:  3     Tidak Ada: 20    Ya   : 89     
##                                                                     
##                                                                     
##                                                                     
##                                                                     
##  akses_internet anggaran_bulanan kerja_kolaborasi  kemauan    skor_kesiapan  
##  Tidak:156      Tidak: 38        Tidak: 68        Tidak: 74   Min.   :2.000  
##  Ya   : 53      Ya   :171        Ya   :141        Ya   :135   1st Qu.:3.000  
##                                                               Median :3.000  
##                                                               Mean   :3.187  
##                                                               3rd Qu.:3.000  
##                                                               Max.   :4.000

Encode variabel

df_preproc$pendidikan <- factor(df_preproc$pendidikan,
                                levels = c('SMP/SMA', 'Diploma', 'Sarjana', 'postgrad'),
                                labels = c(1, 2, 3, 4))

df_preproc$pengalaman_bekerja <- factor(df_preproc$pengalaman_bekerja,
                                levels = c('kurang dari 5 tahun', '6-10 tahun', '11-20 tahun', 'lebih dari 20 tahun'),
                                labels = c(1, 2, 3, 4))
summary(df_preproc)
##       usia       pengalaman_bekerja pendidikan   pekerjaan   keahlian_komputer
##  Min.   :22.00   1:45               1:121      CHW    :140   Bagus   :123     
##  1st Qu.:35.00   2:81               2: 70      Midwife: 69   Terbatas: 86     
##  Median :43.00   3:57               3: 16                                     
##  Mean   :42.41   4:26               4:  2                                     
##  3rd Qu.:50.00                                                                
##  Max.   :64.00                                                                
##  fasilitas_android   aplikasi_di_hp pengalaman_his akses_internet
##  Ada      :206     Ada      :189    Tidak:120      Tidak:156     
##  Tidak Ada:  3     Tidak Ada: 20    Ya   : 89      Ya   : 53     
##                                                                  
##                                                                  
##                                                                  
##                                                                  
##  anggaran_bulanan kerja_kolaborasi  kemauan    skor_kesiapan  
##  Tidak: 38        Tidak: 68        Tidak: 74   Min.   :2.000  
##  Ya   :171        Ya   :141        Ya   :135   1st Qu.:3.000  
##                                                Median :3.000  
##                                                Mean   :3.187  
##                                                3rd Qu.:3.000  
##                                                Max.   :4.000
df_preproc <- df_preproc %>% mutate(pengalaman_bekerja = as.numeric(pengalaman_bekerja),
                                    pendidikan = as.numeric(pendidikan))

One hot encoding

df_onehot <- df_preproc

set.seed(100)
pre_proc <- recipe( ~ ., data = df_onehot) %>% 
                   step_dummy(all_nominal_predictors(), one_hot = T)

d_prep <- pre_proc %>% prep(training = df_onehot, retain = T)
d_prep
## Data Recipe
## 
## Inputs:
## 
##       role #variables
##  predictor         13
## 
## Training data contained 209 data points and no missing data.
## 
## Operations:
## 
## Dummy variables from pekerjaan, keahlian_komputer, ... [trained]
d2 <- juice(d_prep)

df_aftonehot <- sample_n(df_preproc, size = NROW(df_preproc)) # taking 5 random rows

df_final <- bake(d_prep, new_data = df_aftonehot)
summary(df_final)
##       usia       pengalaman_bekerja   pendidikan    skor_kesiapan  
##  Min.   :22.00   Min.   :1.000      Min.   :1.000   Min.   :2.000  
##  1st Qu.:35.00   1st Qu.:2.000      1st Qu.:1.000   1st Qu.:3.000  
##  Median :43.00   Median :2.000      Median :1.000   Median :3.000  
##  Mean   :42.41   Mean   :2.306      Mean   :1.517   Mean   :3.187  
##  3rd Qu.:50.00   3rd Qu.:3.000      3rd Qu.:2.000   3rd Qu.:3.000  
##  Max.   :64.00   Max.   :4.000      Max.   :4.000   Max.   :4.000  
##  pekerjaan_CHW    pekerjaan_Midwife keahlian_komputer_Bagus
##  Min.   :0.0000   Min.   :0.0000    Min.   :0.0000         
##  1st Qu.:0.0000   1st Qu.:0.0000    1st Qu.:0.0000         
##  Median :1.0000   Median :0.0000    Median :1.0000         
##  Mean   :0.6699   Mean   :0.3301    Mean   :0.5885         
##  3rd Qu.:1.0000   3rd Qu.:1.0000    3rd Qu.:1.0000         
##  Max.   :1.0000   Max.   :1.0000    Max.   :1.0000         
##  keahlian_komputer_Terbatas fasilitas_android_Ada fasilitas_android_Tidak.Ada
##  Min.   :0.0000             Min.   :0.0000        Min.   :0.00000            
##  1st Qu.:0.0000             1st Qu.:1.0000        1st Qu.:0.00000            
##  Median :0.0000             Median :1.0000        Median :0.00000            
##  Mean   :0.4115             Mean   :0.9856        Mean   :0.01435            
##  3rd Qu.:1.0000             3rd Qu.:1.0000        3rd Qu.:0.00000            
##  Max.   :1.0000             Max.   :1.0000        Max.   :1.00000            
##  aplikasi_di_hp_Ada aplikasi_di_hp_Tidak.Ada pengalaman_his_Tidak
##  Min.   :0.0000     Min.   :0.00000          Min.   :0.0000      
##  1st Qu.:1.0000     1st Qu.:0.00000          1st Qu.:0.0000      
##  Median :1.0000     Median :0.00000          Median :1.0000      
##  Mean   :0.9043     Mean   :0.09569          Mean   :0.5742      
##  3rd Qu.:1.0000     3rd Qu.:0.00000          3rd Qu.:1.0000      
##  Max.   :1.0000     Max.   :1.00000          Max.   :1.0000      
##  pengalaman_his_Ya akses_internet_Tidak akses_internet_Ya
##  Min.   :0.0000    Min.   :0.0000       Min.   :0.0000   
##  1st Qu.:0.0000    1st Qu.:0.0000       1st Qu.:0.0000   
##  Median :0.0000    Median :1.0000       Median :0.0000   
##  Mean   :0.4258    Mean   :0.7464       Mean   :0.2536   
##  3rd Qu.:1.0000    3rd Qu.:1.0000       3rd Qu.:1.0000   
##  Max.   :1.0000    Max.   :1.0000       Max.   :1.0000   
##  anggaran_bulanan_Tidak anggaran_bulanan_Ya kerja_kolaborasi_Tidak
##  Min.   :0.0000         Min.   :0.0000      Min.   :0.0000        
##  1st Qu.:0.0000         1st Qu.:1.0000      1st Qu.:0.0000        
##  Median :0.0000         Median :1.0000      Median :0.0000        
##  Mean   :0.1818         Mean   :0.8182      Mean   :0.3254        
##  3rd Qu.:0.0000         3rd Qu.:1.0000      3rd Qu.:1.0000        
##  Max.   :1.0000         Max.   :1.0000      Max.   :1.0000        
##  kerja_kolaborasi_Ya kemauan_Tidak      kemauan_Ya    
##  Min.   :0.0000      Min.   :0.0000   Min.   :0.0000  
##  1st Qu.:0.0000      1st Qu.:0.0000   1st Qu.:0.0000  
##  Median :1.0000      Median :0.0000   Median :1.0000  
##  Mean   :0.6746      Mean   :0.3541   Mean   :0.6459  
##  3rd Qu.:1.0000      3rd Qu.:1.0000   3rd Qu.:1.0000  
##  Max.   :1.0000      Max.   :1.0000   Max.   :1.0000

Persiapan clustering

library(cluster)
library(factoextra)
library(dbscan)
library(fpc)
library(NbClust)

Menentukkan jumlah k klaster untuk clara dan kmeans dengan silhouette

fviz_nbclust(df_final, pam, method = "silhouette")+
    theme_update() #Diperoleh k= 2

fviz_nbclust(df_final, kmeans, method = "silhouette")+
    theme_update() #Diperoleh k= 2

K-Medoids/PAM

set.seed(1234)
pam.res <- pam(df_final, 2)
print(pam.res)
## Medoids:
##       ID usia pengalaman_bekerja pendidikan skor_kesiapan pekerjaan_CHW
## [1,] 124   48                  2          1             3             1
## [2,] 200   30                  2          2             3             0
##      pekerjaan_Midwife keahlian_komputer_Bagus keahlian_komputer_Terbatas
## [1,]                 0                       0                          1
## [2,]                 1                       1                          0
##      fasilitas_android_Ada fasilitas_android_Tidak.Ada aplikasi_di_hp_Ada
## [1,]                     1                           0                  1
## [2,]                     1                           0                  1
##      aplikasi_di_hp_Tidak.Ada pengalaman_his_Tidak pengalaman_his_Ya
## [1,]                        0                    1                 0
## [2,]                        0                    0                 1
##      akses_internet_Tidak akses_internet_Ya anggaran_bulanan_Tidak
## [1,]                    1                 0                      0
## [2,]                    1                 0                      0
##      anggaran_bulanan_Ya kerja_kolaborasi_Tidak kerja_kolaborasi_Ya
## [1,]                   1                      1                   0
## [2,]                   1                      0                   1
##      kemauan_Tidak kemauan_Ya
## [1,]             0          1
## [2,]             0          1
## Clustering vector:
##   [1] 1 2 2 1 1 1 1 1 1 1 1 2 1 1 2 1 2 2 1 2 2 1 1 1 1 2 1 2 1 2 2 1 2 1 1 1 2
##  [38] 1 2 1 2 1 1 2 1 1 1 1 1 1 2 2 2 1 1 1 2 2 2 1 1 2 2 1 2 2 1 1 1 2 2 2 2 1
##  [75] 1 1 2 2 1 1 1 1 2 1 1 2 1 1 1 1 1 2 1 1 2 1 1 2 1 1 2 1 1 1 2 2 1 2 1 1 2
## [112] 2 1 1 1 1 1 1 2 1 1 1 2 1 1 1 1 1 2 1 2 1 1 1 1 1 1 2 1 2 1 2 2 1 1 1 1 1
## [149] 1 1 1 1 1 1 2 1 2 1 1 1 2 2 1 1 1 1 2 2 1 1 1 1 2 1 1 2 1 1 1 2 1 2 2 1 2
## [186] 1 1 2 1 1 2 2 1 1 2 1 1 1 1 2 1 2 1 1 2 2 1 1 2
## Objective function:
##    build     swap 
## 6.328449 5.842452 
## 
## Available components:
##  [1] "medoids"    "id.med"     "clustering" "objective"  "isolation" 
##  [6] "clusinfo"   "silinfo"    "diss"       "call"       "data"
# Gabung dengan data awal
pam_klaster <- cbind(df_final, cluster = pam.res$cluster)
pam_klaster <- as.data.frame(pam_klaster)
pam_klaster$cluster <- as.factor(pam_klaster$cluster)
pam_klaster %>% head()
##   usia pengalaman_bekerja pendidikan skor_kesiapan pekerjaan_CHW
## 1   41                  3          2             4             0
## 2   27                  2          2             3             0
## 3   31                  3          2             3             0
## 4   49                  3          1             3             1
## 5   48                  3          1             2             1
## 6   47                  3          1             3             1
##   pekerjaan_Midwife keahlian_komputer_Bagus keahlian_komputer_Terbatas
## 1                 1                       1                          0
## 2                 1                       1                          0
## 3                 1                       1                          0
## 4                 0                       1                          0
## 5                 0                       0                          1
## 6                 0                       0                          1
##   fasilitas_android_Ada fasilitas_android_Tidak.Ada aplikasi_di_hp_Ada
## 1                     1                           0                  1
## 2                     1                           0                  1
## 3                     1                           0                  1
## 4                     1                           0                  1
## 5                     1                           0                  1
## 6                     1                           0                  1
##   aplikasi_di_hp_Tidak.Ada pengalaman_his_Tidak pengalaman_his_Ya
## 1                        0                    1                 0
## 2                        0                    0                 1
## 3                        0                    0                 1
## 4                        0                    0                 1
## 5                        0                    1                 0
## 6                        0                    1                 0
##   akses_internet_Tidak akses_internet_Ya anggaran_bulanan_Tidak
## 1                    0                 1                      1
## 2                    0                 1                      0
## 3                    1                 0                      0
## 4                    1                 0                      0
## 5                    0                 1                      1
## 6                    1                 0                      0
##   anggaran_bulanan_Ya kerja_kolaborasi_Tidak kerja_kolaborasi_Ya kemauan_Tidak
## 1                   0                      0                   1             0
## 2                   1                      0                   1             1
## 3                   1                      0                   1             0
## 4                   1                      0                   1             0
## 5                   0                      1                   0             0
## 6                   1                      1                   0             1
##   kemauan_Ya cluster
## 1          1       1
## 2          0       2
## 3          1       2
## 4          1       1
## 5          1       1
## 6          0       1
# Sedikit visualisasi
ggplot(pam_klaster, aes(x=cluster,y=(usia),color=cluster)) + geom_boxplot()

ggplot(pam_klaster, aes(x=cluster,y=(pengalaman_bekerja), color=cluster)) + geom_boxplot()

ggplot(pam_klaster, aes(x=cluster,y=(pendidikan), color=cluster)) + geom_boxplot()

ggplot(pam_klaster, aes(x=cluster,y=(skor_kesiapan), color=cluster)) + geom_boxplot()

# Summary hasil
pam_klaster %>% group_by(cluster) %>% 
    summarise(usia=median(usia),
              pengalaman_bekerja=median(pengalaman_bekerja),
              pendidikan=median(pendidikan),
              skor_kesiapan=median(skor_kesiapan),
              n_obs = n()) 
## # A tibble: 2 × 6
##   cluster  usia pengalaman_bekerja pendidikan skor_kesiapan n_obs
##   <fct>   <dbl>              <dbl>      <dbl>         <dbl> <int>
## 1 1          48                  3          1             3   136
## 2 2          31                  2          2             3    73

K-Means

set.seed(1234)
km.res <- kmeans(df_final, 2)
print(km.res)
## K-means clustering with 2 clusters of sizes 98, 111
## 
## Cluster means:
##       usia pengalaman_bekerja pendidikan skor_kesiapan pekerjaan_CHW
## 1 33.43878           1.918367   1.714286      3.234694     0.4285714
## 2 50.33333           2.648649   1.342342      3.144144     0.8828829
##   pekerjaan_Midwife keahlian_komputer_Bagus keahlian_komputer_Terbatas
## 1         0.5714286               0.7653061                  0.2346939
## 2         0.1171171               0.4324324                  0.5675676
##   fasilitas_android_Ada fasilitas_android_Tidak.Ada aplikasi_di_hp_Ada
## 1             0.9897959                  0.01020408          0.9489796
## 2             0.9819820                  0.01801802          0.8648649
##   aplikasi_di_hp_Tidak.Ada pengalaman_his_Tidak pengalaman_his_Ya
## 1               0.05102041            0.4693878         0.5306122
## 2               0.13513514            0.6666667         0.3333333
##   akses_internet_Tidak akses_internet_Ya anggaran_bulanan_Tidak
## 1            0.6428571         0.3571429              0.1938776
## 2            0.8378378         0.1621622              0.1711712
##   anggaran_bulanan_Ya kerja_kolaborasi_Tidak kerja_kolaborasi_Ya kemauan_Tidak
## 1           0.8061224              0.2959184           0.7040816     0.3775510
## 2           0.8288288              0.3513514           0.6486486     0.3333333
##   kemauan_Ya
## 1  0.6224490
## 2  0.6666667
## 
## Clustering vector:
##   [1] 1 1 1 2 2 2 2 2 2 1 2 1 2 2 1 2 1 1 2 1 1 2 2 1 2 1 2 1 1 1 1 2 1 2 2 2 1
##  [38] 2 1 1 1 1 2 1 2 2 2 2 2 2 1 1 1 2 2 2 1 1 1 2 2 1 1 1 1 1 2 2 2 1 1 1 1 2
##  [75] 2 2 1 1 2 2 1 1 1 1 1 1 2 2 2 2 2 1 2 2 1 2 2 1 2 2 1 2 2 1 1 1 1 1 2 1 1
## [112] 1 2 2 2 1 2 2 1 2 2 1 1 2 2 1 2 2 1 2 1 2 2 1 2 2 2 1 2 1 2 1 1 2 2 2 1 2
## [149] 1 2 2 2 2 2 1 2 1 2 2 2 1 1 1 2 2 2 1 1 1 2 2 2 1 2 2 1 2 2 2 1 2 1 1 2 1
## [186] 2 2 1 2 2 1 1 2 2 1 2 2 2 2 1 2 1 1 1 1 1 1 2 1
## 
## Within cluster sum of squares by cluster:
## [1] 3715.102 4382.883
##  (between_SS / total_SS =  64.8 %)
## 
## Available components:
## 
## [1] "cluster"      "centers"      "totss"        "withinss"     "tot.withinss"
## [6] "betweenss"    "size"         "iter"         "ifault"
# Gabung dengan data awal
km_klaster <- cbind(df_final, cluster = km.res$cluster)
km_klaster <- as.data.frame(km_klaster)
km_klaster$cluster <- as.factor(km_klaster$cluster)

# Sedikit visualisasi
ggplot(km_klaster, aes(x=cluster,y=(usia),color=cluster)) + geom_boxplot()

ggplot(km_klaster, aes(x=cluster,y=(pengalaman_bekerja), color=cluster)) + geom_boxplot()

ggplot(km_klaster, aes(x=cluster,y=(pendidikan), color=cluster)) + geom_boxplot()

ggplot(km_klaster, aes(x=cluster,y=(skor_kesiapan), color=cluster)) + geom_boxplot()

# Summary hasil
km_klaster %>% group_by(cluster) %>% 
    summarise(usia=median(usia),
              pengalaman_bekerja=median(pengalaman_bekerja),
              pendidikan=median(pendidikan),
              skor_kesiapan=median(skor_kesiapan),
              n_obs = n())
## # A tibble: 2 × 6
##   cluster  usia pengalaman_bekerja pendidikan skor_kesiapan n_obs
##   <fct>   <dbl>              <dbl>      <dbl>         <dbl> <int>
## 1 1          34                  2          2             3    98
## 2 2          50                  3          1             3   111

Evaluasi klaster (Internal Validation)

# Silhouette
sil_pam <- silhouette(pam.res$cluster, dist(df_final))
fviz_silhouette(sil_pam) #  Average silhouette : 0.51
##   cluster size ave.sil.width
## 1       1  136          0.46
## 2       2   73          0.59

sil_km <- silhouette(km.res$cluster, dist(df_final))
fviz_silhouette(sil_km)  #  Average silhouette : 0.52
##   cluster size ave.sil.width
## 1       1   98          0.51
## 2       2  111          0.52

set.seed(1234)
pam_stats <- cluster.stats(dist(df_final), pam.res$cluster)
pam_stats$dunn # Nilai Dunn index = 0.05581456
## [1] 0.05581456
km_stats <- cluster.stats(dist(df_final), km.res$cluster)
km_stats$dunn # Nilai Dunn index = 0.06343615
## [1] 0.06343615

Hasil summary dan visualisasi klaster terbaik : K-Means

fviz_cluster(list(data = df_final, cluster = km.res$cluster),
             ellipse.type = "convex", geom = "point", stand = FALSE,
             palette = "jco") + theme_minimal(base_size = 11 ) + ggtitle("") +
    scale_colour_discrete(name = "Cluster", labels = c("Tidak siap","Siap")) +
  theme_update() + theme(legend.position = "right")
## Scale for 'colour' is already present. Adding another scale for 'colour',
## which will replace the existing scale.

Dua cluster yang terbentuk dinamakan sebagai cluster siap dan tidak siap. Cluster 2 dipilih sebagai cluster siap karena peneliti menitikberatkan perhatian pada variabel terpenting (menurut peneliti) yang mana secara berurutan, yaitu 1. usia, 2. pengalaman bekerja, 3. pendidikan, dan terakhir 4. skor kepuasan.

Kesimpulan

Berdasarkan hasil di atas, diperoleh informasi bahwa:

  1. Tenaga kesehatan yang cukup senior dari segi usia cenderung berada pada cluster siap.

  2. Tenaga kesehatan yang berada pada cluster siap memiliki pengalaman kerja lebih dari 10 tahun. Walaupun begitu, dari segi pendidikan, tenaga kesehatan pada cluster siap rata-rata berpendidikan SMP/SMA.

  3. Dari segi skor kesiapan, cluster siap dan tidak siap memiliki rata-rata yang sama, yaitu bernilai 3.