library(readxl)
## Warning: package 'readxl' was built under R version 4.5.2
wine = read_excel("C:/Users/user/Downloads/Wine_Quality.xlsx")
head(wine)
## # A tibble: 6 × 7
## Clarity Aroma Body Flavor Oakiness Quality Region
## <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
## 1 1 3.3 2.8 3.1 4.1 9.8 1
## 2 1 4.4 4.9 3.5 3.9 12.6 1
## 3 1 3.9 5.3 4.8 4.7 11.9 1
## 4 1 3.9 2.6 3.1 3.6 11.1 1
## 5 1 5.6 5.1 5.5 5.1 13.3 1
## 6 1 4.6 4.7 5 4.1 12.8 1
str(wine)
## tibble [38 × 7] (S3: tbl_df/tbl/data.frame)
## $ Clarity : num [1:38] 1 1 1 1 1 1 1 1 1 1 ...
## $ Aroma : num [1:38] 3.3 4.4 3.9 3.9 5.6 4.6 4.8 5.3 4.3 4.3 ...
## $ Body : num [1:38] 2.8 4.9 5.3 2.6 5.1 4.7 4.8 4.5 4.3 3.9 ...
## $ Flavor : num [1:38] 3.1 3.5 4.8 3.1 5.5 5 4.8 4.3 3.9 4.7 ...
## $ Oakiness: num [1:38] 4.1 3.9 4.7 3.6 5.1 4.1 3.3 5.2 2.9 3.9 ...
## $ Quality : num [1:38] 9.8 12.6 11.9 11.1 13.3 12.8 12.8 12 13.6 13.9 ...
## $ Region : num [1:38] 1 1 1 1 1 1 1 1 3 1 ...
summary(wine)
## Clarity Aroma Body Flavor
## Min. :0.5000 Min. :3.300 Min. :2.600 Min. :2.900
## 1st Qu.:0.8250 1st Qu.:4.125 1st Qu.:4.150 1st Qu.:4.225
## Median :1.0000 Median :4.650 Median :4.750 Median :4.800
## Mean :0.9237 Mean :4.847 Mean :4.684 Mean :4.768
## 3rd Qu.:1.0000 3rd Qu.:5.450 3rd Qu.:5.375 3rd Qu.:5.500
## Max. :1.0000 Max. :7.700 Max. :6.600 Max. :7.000
## Oakiness Quality Region
## Min. :2.900 Min. : 7.90 Min. :1.000
## 1st Qu.:3.700 1st Qu.:11.15 1st Qu.:1.000
## Median :4.100 Median :12.45 Median :2.000
## Mean :4.255 Mean :12.44 Mean :1.868
## 3rd Qu.:4.775 3rd Qu.:13.75 3rd Qu.:3.000
## Max. :6.000 Max. :16.10 Max. :3.000
## Matriks scatterplot semua variabel sekaligus
pairs(wine, main = "Matriks Scatterplot - Wine Quality Data",
pch = 19, col = "steelblue")

## Scatterplot Quality vs masing-masing prediktor + garis regresi
par(mfrow = c(2, 3))
prediktor <- c("Clarity", "Aroma", "Body", "Flavor", "Oakiness")
for (p in prediktor) {
plot(wine[[p]], wine$Quality,
xlab = p, ylab = "Quality",
main = paste("Quality vs", p,
"\n(r =", round(cor(wine[[p]], wine$Quality), 3), ")"),
pch = 19, col = "darkslategray")
abline(lm(wine$Quality ~ wine[[p]]), col = "red", lwd = 2)
}
par(mfrow = c(1, 1))

## Matriks korelasi
korelasi <- cor(wine)
round(korelasi, 3)
## Clarity Aroma Body Flavor Oakiness Quality Region
## Clarity 1.000 0.062 -0.308 -0.085 0.183 0.028 -0.020
## Aroma 0.062 1.000 0.549 0.737 0.202 0.707 0.620
## Body -0.308 0.549 1.000 0.647 0.152 0.549 0.435
## Flavor -0.085 0.737 0.647 1.000 0.180 0.790 0.506
## Oakiness 0.183 0.202 0.152 0.180 1.000 -0.047 -0.060
## Quality 0.028 0.707 0.549 0.790 -0.047 1.000 0.507
## Region -0.020 0.620 0.435 0.506 -0.060 0.507 1.000
## Heatmap korelasi (opsional, butuh package corrplot)
# install.packages("corrplot")
library(corrplot)
## Warning: package 'corrplot' was built under R version 4.5.3
## corrplot 0.95 loaded
corrplot(korelasi, method = "color", type = "upper",
addCoef.col = "black", tl.col = "black", number.cex = 0.8,
title = "Matriks Korelasi Antarvariabel", mar = c(0,0,2,0))

model <- lm(Quality ~ Clarity + Aroma + Body + Flavor + Oakiness, data = wine)
summary(model)
##
## Call:
## lm(formula = Quality ~ Clarity + Aroma + Body + Flavor + Oakiness,
## data = wine)
##
## Residuals:
## Min 1Q Median 3Q Max
## -2.85552 -0.57448 -0.07092 0.67275 1.68093
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 3.9969 2.2318 1.791 0.082775 .
## Clarity 2.3395 1.7348 1.349 0.186958
## Aroma 0.4826 0.2724 1.771 0.086058 .
## Body 0.2732 0.3326 0.821 0.417503
## Flavor 1.1683 0.3045 3.837 0.000552 ***
## Oakiness -0.6840 0.2712 -2.522 0.016833 *
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 1.163 on 32 degrees of freedom
## Multiple R-squared: 0.7206, Adjusted R-squared: 0.6769
## F-statistic: 16.51 on 5 and 32 DF, p-value: 4.703e-08
coef(model)
## (Intercept) Clarity Aroma Body Flavor Oakiness
## 3.9968648 2.3394535 0.4825505 0.2731612 1.1683238 -0.6840102
## Persamaan model:
## Quality_hat = 4.2147 + 0.6998*Clarity + 0.6295*Aroma + 0.7058*Body
## + 0.7317*Flavor - 0.5295*Oakiness
## Selang kepercayaan koefisien
confint(model, level = 0.95)
## 2.5 % 97.5 %
## (Intercept) -0.54910206 8.5428317
## Clarity -1.19427368 5.8731807
## Aroma -0.07240642 1.0375075
## Body -0.40424262 0.9505650
## Flavor 0.54811681 1.7885307
## Oakiness -1.23641174 -0.1316086
## Tabel ANAVA overall (regresi vs residual)
anova_overall <- anova(model)
print(anova_overall)
## Analysis of Variance Table
##
## Response: Quality
## Df Sum Sq Mean Sq F value Pr(>F)
## Clarity 1 0.125 0.125 0.0926 0.7628120
## Aroma 1 77.353 77.353 57.2351 1.286e-08 ***
## Body 1 6.414 6.414 4.7461 0.0368417 *
## Flavor 1 19.050 19.050 14.0953 0.0006946 ***
## Oakiness 1 8.598 8.598 6.3616 0.0168327 *
## Residuals 32 43.248 1.352
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
## Ringkas jadi tabel Regresi - Residual - Total
SSR <- sum(anova_overall$"Sum Sq"[1:5]) # jumlah kuadrat regresi
SSE <- anova_overall$"Sum Sq"[6] # jumlah kuadrat residual
SST <- SSR + SSE
dfR <- sum(anova_overall$Df[1:5])
dfE <- anova_overall$Df[6]
dfT <- dfR + dfE
MSR <- SSR / dfR
MSE <- SSE / dfE
Fhitung <- MSR / MSE
pvalue <- 1 - pf(Fhitung, dfR, dfE)
tabel_anava <- data.frame(
Sumber = c("Regresi", "Residual", "Total"),
db = c(dfR, dfE, dfT),
JK = c(SSR, SSE, SST),
KT = c(MSR, MSE, NA),
Fhitung = c(Fhitung, NA, NA),
pvalue = c(pvalue, NA, NA)
)
print(tabel_anava, digits = 5)
## Sumber db JK KT Fhitung pvalue
## 1 Regresi 5 111.540 22.3081 16.506 4.703e-08
## 2 Residual 32 43.248 1.3515 NA NA
## 3 Total 37 154.788 NA NA NA
## Nilai F tabel pada alpha = 5%
alpha <- 0.05
F_tabel <- qf(1 - alpha, dfR, dfE)
cat("F_tabel(alpha=0.05, db1=", dfR, ", db2=", dfE, ") =", F_tabel, "\n")
## F_tabel(alpha=0.05, db1= 5 , db2= 32 ) = 2.512255
cat("F_hitung =", Fhitung, "\n")
## F_hitung = 16.50616
cat("Keputusan:", ifelse(Fhitung > F_tabel,
"Tolak H0 -> model signifikan",
"Gagal tolak H0 -> model tidak signifikan"), "\n")
## Keputusan: Tolak H0 -> model signifikan
## R-squared dan Adjusted R-squared
cat("R-squared :", summary(model)$r.squared, "\n")
## R-squared : 0.7205992
cat("Adj R-squared :", summary(model)$adj.r.squared, "\n")
## Adj R-squared : 0.6769428
library(corrplot)
shapiro.test(model$residuals)
##
## Shapiro-Wilk normality test
##
## data: model$residuals
## W = 0.96621, p-value = 0.3
library(lmtest)
## Warning: package 'lmtest' was built under R version 4.5.3
## Loading required package: zoo
## Warning: package 'zoo' was built under R version 4.5.3
##
## Attaching package: 'zoo'
## The following objects are masked from 'package:base':
##
## as.Date, as.Date.numeric
bptest(model)
##
## studentized Breusch-Pagan test
##
## data: model
## BP = 10.022, df = 5, p-value = 0.07461
library(car)
## Warning: package 'car' was built under R version 4.5.3
## Loading required package: carData
## Warning: package 'carData' was built under R version 4.5.3
vif(model)
## Clarity Aroma Body Flavor Oakiness
## 1.266390 2.381143 2.056492 2.682277 1.096731
# =========================================================
# NO. 5 - IDENTIFIKASI OUTLIER
# =========================================================
# 1. Studentized residual
rstudent(model)
## 1 2 3 4 5 6
## 0.268915086 1.310570723 -0.147746834 0.989111532 -0.060824579 -0.067222376
## 7 8 9 10 11 12
## -0.462322650 0.368774378 1.367233491 1.461038927 1.488413844 1.712995605
## 13 14 15 16 17 18
## 0.429535178 -0.370917971 0.549437274 1.522681696 0.451182841 -0.065376408
## 19 20 21 22 23 24
## -1.178448030 -3.087312700 0.005924868 -0.472759465 -1.511289638 -1.203178648
## 25 26 27 28 29 30
## -1.314046275 -0.182564885 -0.075993468 -0.519019437 -1.345569135 -1.701955694
## 31 32 33 34 35 36
## -1.019544790 -0.119034824 1.200175907 0.427954051 0.465967589 0.646531035
## 37 38
## 0.792354831 -0.685642649
# Mencari observasi dengan studentized residual paling ekstrem
which.max(abs(rstudent(model)))
## 20
## 20
# Nilai studentized residual observasi tersebut
rstudent(model)[which.max(abs(rstudent(model)))]
## 20
## -3.087313
# 2. Cook's Distance
cooks.distance(model)
## 1 2 3 4 5 6
## 2.540574e-03 5.358209e-02 7.575551e-04 4.757193e-02 5.239139e-05 4.724372e-05
## 7 8 9 10 11 12
## 4.344657e-03 2.882056e-03 5.581593e-02 3.040021e-02 2.902936e-02 3.007018e-01
## 13 14 15 16 17 18
## 7.672432e-03 1.321196e-02 1.604877e-02 2.416940e-02 6.591579e-03 9.192882e-05
## 19 20 21 22 23 24
## 3.039585e-02 3.101434e-01 8.646330e-07 3.742266e-03 9.605977e-02 5.139300e-02
## 25 26 27 28 29 30
## 2.345999e-02 4.632939e-04 2.289592e-04 3.400519e-03 3.876841e-02 1.012302e-01
## 31 32 33 34 35 36
## 4.397236e-02 7.313842e-04 4.537606e-02 5.720638e-03 4.287351e-03 1.025008e-02
## 37 38
## 6.359374e-02 1.079912e-02
# Mencari observasi dengan Cook's Distance terbesar
which.max(cooks.distance(model))
## 20
## 20
# Nilai Cook's Distance terbesar
max(cooks.distance(model))
## [1] 0.3101434
# 3. Melihat data observasi yang teridentifikasi
wine[which.max(abs(rstudent(model))), ]
## # A tibble: 1 × 7
## Clarity Aroma Body Flavor Oakiness Quality Region
## <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
## 1 0.9 3.4 5 3.4 3.4 7.9 2
# =========================================================
# NO. 6 - VARIABEL YANG MEMPENGARUHI RESPONSE
# =========================================================
# Melihat hasil uji parsial masing-masing variabel
summary(model)
##
## Call:
## lm(formula = Quality ~ Clarity + Aroma + Body + Flavor + Oakiness,
## data = wine)
##
## Residuals:
## Min 1Q Median 3Q Max
## -2.85552 -0.57448 -0.07092 0.67275 1.68093
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 3.9969 2.2318 1.791 0.082775 .
## Clarity 2.3395 1.7348 1.349 0.186958
## Aroma 0.4826 0.2724 1.771 0.086058 .
## Body 0.2732 0.3326 0.821 0.417503
## Flavor 1.1683 0.3045 3.837 0.000552 ***
## Oakiness -0.6840 0.2712 -2.522 0.016833 *
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 1.163 on 32 degrees of freedom
## Multiple R-squared: 0.7206, Adjusted R-squared: 0.6769
## F-statistic: 16.51 on 5 and 32 DF, p-value: 4.703e-08
# Mengambil koefisien dan p-value
coef(summary(model))
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 3.9968648 2.2317701 1.7908945 0.0827745402
## Clarity 2.3394535 1.7348271 1.3485226 0.1869578145
## Aroma 0.4825505 0.2724473 1.7711703 0.0860575292
## Body 0.2731612 0.3325606 0.8213876 0.4175033004
## Flavor 1.1683238 0.3044807 3.8371025 0.0005522334
## Oakiness -0.6840102 0.2711928 -2.5222287 0.0168327190