2025-10-19
Title
Linear regression — simple and multiple. Visualizations with ggplot2 and an interactive 3D plotly example.
Simple linear model (math) 𝑦 𝑖 = 𝛽 0 + 𝛽 1 𝑥 𝑖 + 𝜀 𝑖 , 𝜀 𝑖 ∼ 𝑁 ( 0 , 𝜎 2 ) y i
=β 0
+β 1
x i
+ε i
,ε i
∼N(0,σ 2 ) Matrix form (math) 𝑦 = 𝑋 𝛽 + 𝜀 , 𝛽 ^ = ( 𝑋 ⊤ 𝑋 ) − 1 𝑋 ⊤ 𝑦 y=Xβ+ε, β ^
=(X ⊤ X) −1 X ⊤ y Data generation and model fit Writing
n <- 120 x <- runif(n, 0, 10) y <- 5 + 1.8 * x + rnorm(n, sd = 3) data <- data.frame(x = x, y = y) model <- lm(y ~ x, data = data) summary(model)
Scatter plot + OLS line (ggplot) Writing
ggplot(data, aes(x = x, y = y)) + geom_point() + geom_smooth(method = “lm”, se = FALSE, color = “red”) + labs(title = “Scatter plot and OLS fit”, x = “x”, y = “y”)
Residuals vs fitted (ggplot) Writing
resid_df <- data.frame(fitted = fitted(model), resid = residuals(model)) ggplot(resid_df, aes(x = fitted, y = resid)) + geom_point() + geom_hline(yintercept = 0, linetype = “dashed”) + labs(title = “Residuals vs Fitted”, x = “Fitted values”, y = “Residuals”)
Residual diagnostics Writing
p1 <- ggplot(resid_df, aes(x = resid)) + geom_histogram(bins = 20) + labs(title = “Residuals histogram”, x = “Residual”) p2 <- ggplot(resid_df, aes(sample = resid)) + stat_qq() + stat_qq_line() + labs(title = “Normal Q-Q”) print(p1) print(p2)
Multiple regression demo (data generation) Writing
x1 <- runif(100, 0, 10) x2 <- runif(100, 0, 10) y3d <- 3 + 1.5 * x1 + 2 * x2 + rnorm(100, sd = 2) df3d <- data.frame(x1 = x1, x2 = x2, y3d = y3d)
3D interactive plot (plotly) Writing
plot_ly(df3d, x = ~x1, y = ~x2, z = ~y3d, type = “scatter3d”, mode = “markers”, marker = list(size = 3)) %>% layout(title = “3D Scatter: y ~ x1 + x2”, scene = list(xaxis = list(title = “x1”), yaxis = list(title = “x2”), zaxis = list(title = “y”)))
Hypothesis testing (math) 𝐻 0 : 𝛽 1 = 0 vs 𝐻 𝑎 : 𝛽 1 ≠ 0 H 0
:β 1
=0vsH a
:β 1
=0 𝑡 = 𝛽 ^ 1 S E ( 𝛽 ^ 1 ) ∼ 𝑡 𝑛 − 2 t= SE( β ^
1
) β ^
1
∼t n−2
Reproducible code slide Writing
library(ggplot2) ggplot(data, aes(x = x, y = y)) + geom_point() + geom_smooth(method = “lm”, se = FALSE, color = “red”) + labs(title = “Scatter plot and OLS fit”, x = “x”, y = “y”)
Conclusion