COSMOS logo

Linear Regression

Zhaoxia Yu

Load packages, read data

Code
library(ggplot2)
library(tidyverse)

alzheimer_data <- read.csv("https://raw.githubusercontent.com/COSMOS-DataScience/slides/refs/heads/main/data/alzheimer_data.csv", head=T) %>% 
  select(id, diagnosis, age, educ, female, height, weight, lhippo, rhippo) %>% 
  mutate(diagnosis = as.factor(diagnosis), 
         female = as.factor(female),
         hippo=lhippo+rhippo)


alzheimer_healthy <- read.csv("https://raw.githubusercontent.com/COSMOS-DataScience/slides/refs/heads/main/data/alzheimer_data.csv", head=T) %>% 
  mutate(hippo=lhippo+rhippo, 
         diagnosis = as.factor(diagnosis), 
         female = as.factor(female)) %>% filter(diagnosis==0)


#define the subset of older (>45) healthy subjects
alzheimer_healthy_old <- alzheimer_healthy %>% filter(age>45)

Outline

  • Introduction
    • Correlation and Linear Regression
  • Linear Regression
    • The Response Variable
    • One explanatory variable
      • Ex1. A numerical X: hippo ~ age
      • Ex2. A Binary X: hippo ~ female
      • Ex3. A categorical Variables X: hippo ~ diagnosis

Outline

  • Multiple Linear Regression
    • Motivating Example
    • Can the difference be explained by height?
  • Outliers and model Diagnostics
  • Advanced Topics
    • Interactions
    • Transform \(X\) and \(Y\)

Introduction

Review: Example 6 of Day 5

  • Question: Is hippocampal volume correlated with age in healthy adults?

  • We mentioned a correlation test, but we did not discuss the details the relationship between hippocampal volume and age.

  • Is linear appropriate for the whole age range? What about the age range of 45+?

  • How can be better understand the relationship between hippocampal volume and age? Correlation doesn’t provide an answer to this question. We need linear regression.

Example: Left vs Right Hippocampal Volume

Code
#plot(alzheimer_healthy$age, alzheimer_healthy$hippo, xlab="age", ylab="hippo")

ggplot(alzheimer_healthy, aes(x=age, y=hippo)) +
  geom_point() + 
  labs(x = "age", y="hippo volume", title="hippo volume vs age")
  • The relationship is roughly (negatively) linear except for age <45.

Linear Relationship

Code
ggplot(alzheimer_healthy, aes(x=lhippo, y=rhippo)) +
  geom_point() + 
  labs(x = "left hippo", y="right hippo", title="hippo volume")

Strong vs Weak Linear Relationship

Code
par(mfrow=c(1,2))
plot(alzheimer_healthy$lhippo, alzheimer_healthy$rhippo,
     xlab = "left hippo", ylab="right hippo", main="hippo volume")
plot(alzheimer_healthy$weight, alzheimer_healthy$hippo,
     xlab = "weight", ylab="hippo", main="hippo vs weight")

Correlation vs Linear Regression

  • Correlation is a measure of the strength of linear relationship between two continuous variables.

Correlation between left and right hippo volume

Code
cor(alzheimer_healthy$lhippo, alzheimer_healthy$rhippo)
[1] 0.8626165

Correlation between weight and hippo volume

Code
cor(alzheimer_healthy$weight, alzheimer_healthy$hippo)
[1] 0.270462

Why Is Linear Regression Useful?

  • Understand relationships: Quantify how the expected outcome changes as a predictor changes.

    • Example: How much does the expected hippocampal volume change with a one-year increase in age?
  • Adjust for other variables: Estimate the effect of one predictor while accounting for other relevant variables.

    • This is especially important in observational studies, where many factors may influence the outcome.
  • Make predictions: Predict the expected outcome for a new individual.

    -Example: What is the predicted hippocampal volume for a 46-year-old healthy woman?

Linear Regression

The Response Variable

  • In a linear model, the response variable is the variable that we are trying to predict or explain.

  • A response variable is also known as a dependent variable.

  • It is the outcome or the variable that is being studied and modeled as a function of one or more explanatory (independent) variables.

  • We often use \(y\) to represent the response variable.

Simple Linear Regression (SLM)

Simple Linear Regression

  • It is the regression model with only one \(x\) (explanatory variable).

  • It can be used to assess the linear relationship between two variables. Example, age and hippocampal volume in healthy older (45+) subjects

Code
ggplot(alzheimer_healthy_old, aes(x=age, y=hippo)) +
  geom_point() + 
  labs(x = "age", y="hippo", title="hippo volume vs age in healthy older subjects (45+)")

The Model

  • The linear model is represented as:

\[y=\beta_0 + \beta_1 x + \epsilon\]

  • \(y\): Response variable (dependent variable)

  • \(x\): Explanatory variable (independent variable)

  • \(\beta_0\): Intercept (constant term)

  • \(\beta_1\): Slope (rate of change)

  • \(\epsilon\): Error term (residuals)

  • It is also common to add subject indices: \(y_i=\beta_0 + \beta_1 x_i + \epsilon_i, i=1, \cdots, n\)

Model Assumptions

  • \(y_i=\beta_0 + \beta_1 x_i + \epsilon_i, i=1, \cdots, n\)
  • The \(n\) observations are independent
  • Reasonably large \(n\) or normality assumption for \(\epsilon_i\)
  • Homogeneous variance: \(\epsilon_i \sim N(0, \sigma^2)\). Note that this assumption implies that \(Var(y_i)=\sigma^2\).
  • This is assumption is also known as homoscedasticity.

Least Squares Estimate

  • The most common method to estimate \(\beta_0\) and \(\beta_1\) is the least squares estimate.

  • The least squares estimate minimizes the sum of squared residuals, which is the difference between the observed values and the predicted values.

  • Among all possible lines we can pass through the data, the regression lines has the smallest Residual Sum of Squares.

Least Squares Estimate

What does LSE Do?

Least Squares Estimate: Formulars

  • Least Squares Estimate: looking for \(\hat\beta_0\) and \(\hat\beta_1\) that minimizes \(\sum_{i=1}^n (y_i - \beta_0 -\beta_1 x_i)^2\).

  • Other notations: \[b_0=\hat \beta_0, b_1=\hat\beta_1\]

  • The process of finding \((b_0, b_1)\) involves solving two linear equations jointly.

    • \(b_0=\hat\beta_0=\bar{y}-b_1\bar{x}\)
    • \(b_1=\hat\beta_1=\dfrac{\sum_{i=1}^{n}(x_i-\bar{x})(y_i- \bar{y})}{\sum_{i=1}^{n}(x_i-\bar{x})^2}\)

Interpretation of Simple Linear Regression

Ex 1: hippo ~ age

Code
#define an lm object
obj.age.hippo=lm(hippo~age, data=alzheimer_healthy_old)
summary(obj.age.hippo) 

Call:
lm(formula = hippo ~ age, data = alzheimer_healthy_old)

Residuals:
    Min      1Q  Median      3Q     Max 
-2.6858 -0.4791 -0.0159  0.4793  2.7005 

Coefficients:
             Estimate Std. Error t value Pr(>|t|)    
(Intercept)  8.420392   0.126407   66.61   <2e-16 ***
age         -0.029090   0.001818  -16.00   <2e-16 ***
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 0.7131 on 1477 degrees of freedom
Multiple R-squared:  0.1478,    Adjusted R-squared:  0.1472 
F-statistic: 256.2 on 1 and 1477 DF,  p-value: < 2.2e-16

Ex 1: The Fitted Line

  • The fitted line is \(hippo = 8.42 - 0.029 \times age\)
Code
ggplot(alzheimer_healthy_old, aes(x=age, y=hippo)) +
  geom_point() + 
  labs(x = "age", y="hippo", title="hippo vs age")+
   geom_smooth(method='lm', se=FALSE)

Ex 1: Interpret the Intercept

  • Interpretation of \(b_0=8.42\)
    • mathematically, it is the estimated hippocampal value for a person at age=0.
    • statistically, this interpretation involves extrapolation, which should be avoided. Rational:
      • The linear trend we observed is for healthy subjects who are 45 or older.
      • It is dangerous to assume that the same linear trend holds at around age 0.

Ex 1: The Slope

  • How to interpret \(b_1= - 0.029\)?

  • What if we increase age by 1 year?

  • Recall that the fitted line is \(hippo = 8.42 - 0.029 \times age\)

    • \(hippo_0 = 8.42 - 0.029 \times x\)
    • \(hippo_1 = 8.42 - 0.029 \times (x+1)\)
  • Therefore, \(hippo_1 - hippo_0 = -0.029\), which means that the estimated hippocampal volume decreases by 0.029 cc for each additional year of age.

  • When reporting an estimated slope, it is also important to report uncertainty, such as standard error, confidence interval, and p-value. See next five slides.

Residuals

  • \(e_i = y_i - \hat y_i\) where \(\hat y_i = \hat\beta_0 + \hat \beta_1 x_i\)
  • Residual sum of squares (RSS): \(RSS=\sum_{i=1}^n e_i^2 = \sum_{i=1}^n (y_i -\hat y_i)^2\)
  • An unbiased estimate of \(\sigma^2\) is \(s^2\): \[s^2= \frac{RSS}{n-2}\]

Standard Error and Confidence Interval

  • The standard error of \(\hat\beta_1\) is \[se(\hat \beta_1)=\frac{\sqrt{s^2}}{\sqrt{\sum (x_i - \bar{x})^2}}\]
  • A \(100(1-\alpha)\%\) confidence interval for \(\beta_1\) is \[\hat\beta_1 \pm t_{1-\alpha / 2, n - 2} se(\hat\beta_1)\]

Ex 1: SE and p-value

  • The estimated slope (\(b_1\)) is -0.029, its standard error is 0.001818, and the p-value is \(<2e-16\); the linear relationship is significant at level 0.05.
Code
summary(obj.age.hippo)$coefficients
               Estimate  Std. Error   t value     Pr(>|t|)
(Intercept)  8.42039161 0.126407343  66.61315 0.000000e+00
age         -0.02908978 0.001817536 -16.00506 2.725429e-53

Ex 1: Confidence Interval

  • The estimated slope (\(b_1\)) is -0.029.
  • A 95% confidence interval is (-0.033, -0.026).
Code
confint(obj.age.hippo)
                  2.5 %      97.5 %
(Intercept)  8.17243458  8.66834865
age         -0.03265501 -0.02552456

Estimation vs Prediction

  • Why are the answers to the following two questions different?

  • Question 1: What is the estimated mean hippocampal volume for 46-year-old women?

Code
predict(obj.age.hippo, newdata = data.frame(age=46), interval = 'confidence')
       fit     lwr      upr
1 7.082262 6.99322 7.171303
  • Question 2: What is the predicted hippocampal volume for a 46-year-old woman?
Code
predict(obj.age.hippo, newdata = data.frame(age=46), interval = 'predict')
       fit      lwr      upr
1 7.082262 5.680708 8.483815

Ex 2: A Binary X

  • Now, consider the relationship between hippocampal volume and gender (the female variable in the data)
Code
ggplot(alzheimer_healthy_old, aes(x=female, y=hippo)) +
  geom_point() + 
  labs(x = "female", y="hippo", title="hippo vs female")+
   geom_smooth(method='lm', se=FALSE)

Ex2: Boxplots by gender are better

Code
ggplot(alzheimer_healthy_old, aes(x=female, y=hippo, fill=female)) +
  geom_boxplot() + 
  labs(x = "female", y="hippo", title="hippo vs female")

Ex2: Intercept and Slope

Ex2: Summarize Results and CI

Code
# Fit model
fit <- lm(hippo ~ female, data = alzheimer_healthy_old)

# Coefficient estimates
summary(fit)$coefficients
              Estimate Std. Error   t value     Pr(>|t|)
(Intercept)  6.7356917 0.03272826 205.80660 0.000000e+00
female1     -0.4821982 0.04039219 -11.93791 1.990249e-31
Code
# 95% confidence intervals
confint(fit)
                 2.5 %     97.5 %
(Intercept)  6.6714929  6.7998905
female1     -0.5614304 -0.4029661

Ex2: Results and Interpretation

  • The slope \(b_1=-0.4887882\) is the estimated difference between women and men in hippocampal volume

  • In summary,

    • estimated mean hippocampal volume for men: 6.748
    • estimated mean hippocampal volume for women: 6.748-0.489=6.259
  • Intercept: \(b_0=6.74\) is the estimated hippocampal volume for men (female=0) and its SE is 0.033.

  • Slope (female coefficient): Women have an estimated mean hippocampal volume that is 0.482 units lower than men (SE = 0.040; P < 0.001).

  • In a simple linear regression, when \(x\) is a binary variable, the estimated slope is the mean difference between the two groups.

  • Let’s verify this using two-sample t-test

Code
t.test(hippo~female, data=alzheimer_healthy_old, var.equal =T)

    Two Sample t-test

data:  hippo by female
t = 11.938, df = 1477, p-value < 2.2e-16
alternative hypothesis: true difference in means between group 0 and group 1 is not equal to 0
95 percent confidence interval:
 0.4029661 0.5614304
sample estimates:
mean in group 0 mean in group 1 
       6.735692        6.253494 

Categorical Variables in Linear Regression

  • Categorical variables can be included in linear regression models as factors.
  • Consider the dignosis variable in the alzheimer data, which has three levels: 0 (healthy), 1 (MCI), and 2 (AD).
  • What happens if we use it as a numeric variable (this might not be appropriate in many situations)
  • What happens if we use it as a categorical variable (this is the most appropriate way in this case).

Ex3: When mistakenly treating diagonosis as a numerical variable

  • When using the numerical coding, the model assumes a linear relationship between diagnosis and hippocampal volume:
    • It assumes that mean difference between MCI and healthy is the same as the mean difference between AD and MCI.
    • This might not be the most appropriate way.
Code
alzheimer_data <- read.csv("https://raw.githubusercontent.com/COSMOS-DataScience/slides/refs/heads/main/data/alzheimer_data.csv", head=T) %>% 
  select(id, diagnosis, age, educ, female, height, weight, lhippo, rhippo) %>% 
#  mutate(diagnosis = as.factor(diagnosis), female = as.factor(female), hippo=lhippo+rhippo)
  mutate(hippo=lhippo+rhippo)

#Note that factor here was not treated as a categorical variable, it is treated a numerical variable
summary(lm(hippo ~ diagnosis, data=alzheimer_data))

Call:
lm(formula = hippo ~ diagnosis, data = alzheimer_data)

Residuals:
    Min      1Q  Median      3Q     Max 
-4.5296 -0.5940 -0.0046  0.5760  3.4734 

Coefficients:
            Estimate Std. Error t value Pr(>|t|)    
(Intercept)  6.41399    0.02154   297.7   <2e-16 ***
diagnosis   -0.46342    0.02106   -22.0   <2e-16 ***
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 0.8761 on 2698 degrees of freedom
Multiple R-squared:  0.1522,    Adjusted R-squared:  0.1518 
F-statistic: 484.2 on 1 and 2698 DF,  p-value: < 2.2e-16

Ex3: When mistakenly treating diagonosis as a numerical variable

Code
alzheimer_data <- read.csv("https://raw.githubusercontent.com/COSMOS-DataScience/slides/refs/heads/main/data/alzheimer_data.csv", head=T) %>% 
  select(id, diagnosis, age, educ, female, height, weight, lhippo, rhippo) %>% mutate(female = as.factor(female), hippo = lhippo + rhippo)

# Fit model treating diagnosis as factor
fit <- lm(hippo ~ diagnosis, data = alzheimer_data)
coefs <- coef(fit)

# Model-based means for each group
model_means <- data.frame(
  diagnosis = c("Healthy", "MCI", "AD"),
  hippo = c(coefs[1], coefs[1] + coefs[2], coefs[1] + 2*coefs[2]),
  label = c("b0", "b0 + b1", "b0 + 2*b1")
)

alzheimer_data <- mutate(alzheimer_data, diagnosis = factor(diagnosis, levels=c("0","1","2"), labels = c("Healthy", "MCI", "AD")))
# Plot
ggplot(alzheimer_data, aes(x = diagnosis, y = hippo)) +
  geom_boxplot(fill = "#dceeff", outlier.shape = NA) +
  
  # Add model-predicted means and connect them
  geom_point(data = model_means, aes(y = hippo), color = "red", size = 3) +
  geom_line(data = model_means, aes( y = hippo, group = 1), color = "black", linewidth = 1) +
  
  # Label model means
  geom_text(data = model_means, aes(x=1:3+0.2,y = hippo + 0.5, label = label), color = "red", size = 4) +
  
  labs(
    x = "Diagnosis",
    y = "Total Hippocampal Volume",
    title = "Linear Model Estimates with Diagnosis as Numerical"
  ) +
  theme_minimal()

Use diagnosis as a Categorical Variables in Linear Regression

  • Instead, we can treat diagnosis as a categorical variable (factor).

  • R automatically does dummy coding to create two binary variables: one for MCI and one for AD, with healthy as the reference group.

In this example

  • The estimated intercept is the estimated mean for the reference group (healthy, diagnosis=1).

  • The two slopes are represent the estimated difference between each diagnosis group and the reference group (healthy).

  • Based on the following R output, the estimated mean for healthy is ( ), for MCI is ( ), and for AD is ( ).

Code
alzheimer_data <- read.csv("https://raw.githubusercontent.com/COSMOS-DataScience/slides/refs/heads/main/data/alzheimer_data.csv", head=T) %>% 
  select(id, diagnosis, age, educ, female, height, weight, lhippo, rhippo) %>% 
  mutate(diagnosis = as.factor(diagnosis), female = as.factor(female), hippo=lhippo+rhippo)

summary(lm(hippo ~ diagnosis, data=alzheimer_data))

Call:
lm(formula = hippo ~ diagnosis, data = alzheimer_data)

Residuals:
    Min      1Q  Median      3Q     Max 
-4.5797 -0.5862 -0.0074  0.5770  3.4233 

Coefficients:
            Estimate Std. Error t value Pr(>|t|)    
(Intercept)  6.43207    0.02234  287.97   <2e-16 ***
diagnosis1  -0.57198    0.04180  -13.68   <2e-16 ***
diagnosis2  -0.89476    0.04339  -20.62   <2e-16 ***
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 0.8748 on 2697 degrees of freedom
Multiple R-squared:  0.155, Adjusted R-squared:  0.1544 
F-statistic: 247.3 on 2 and 2697 DF,  p-value: < 2.2e-16

Ex3: Recode diagnosis

  • We can also recode the values of diagnosis to make it more readable.
Code
alzheimer_data <- alzheimer_data %>% 
  mutate(diagnosis = recode(diagnosis, `0` = "Healthy", `1` = "MCI", `2` = "AD"), hippo=lhippo+rhippo)
summary(lm(hippo ~ diagnosis, data=alzheimer_data))

Call:
lm(formula = hippo ~ diagnosis, data = alzheimer_data)

Residuals:
    Min      1Q  Median      3Q     Max 
-4.5797 -0.5862 -0.0074  0.5770  3.4233 

Coefficients:
             Estimate Std. Error t value Pr(>|t|)    
(Intercept)   6.43207    0.02234  287.97   <2e-16 ***
diagnosisMCI -0.57198    0.04180  -13.68   <2e-16 ***
diagnosisAD  -0.89476    0.04339  -20.62   <2e-16 ***
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 0.8748 on 2697 degrees of freedom
Multiple R-squared:  0.155, Adjusted R-squared:  0.1544 
F-statistic: 247.3 on 2 and 2697 DF,  p-value: < 2.2e-16

Change Reference Group

  • If we want to use the AD group as the reference group, we can use the relevel function to change the reference level of the factor variable.
Code
alzheimer_data <- alzheimer_data %>% 
  mutate(diagnosis = relevel(diagnosis, ref = "AD"), hippo=lhippo+rhippo)
summary(lm(hippo ~ diagnosis, data=alzheimer_data))

Call:
lm(formula = hippo ~ diagnosis, data = alzheimer_data)

Residuals:
    Min      1Q  Median      3Q     Max 
-4.5797 -0.5862 -0.0074  0.5770  3.4233 

Coefficients:
                 Estimate Std. Error t value Pr(>|t|)    
(Intercept)       5.53731    0.03720 148.849  < 2e-16 ***
diagnosisHealthy  0.89476    0.04339  20.621  < 2e-16 ***
diagnosisMCI      0.32278    0.05131   6.291 3.66e-10 ***
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 0.8748 on 2697 degrees of freedom
Multiple R-squared:  0.155, Adjusted R-squared:  0.1544 
F-statistic: 247.3 on 2 and 2697 DF,  p-value: < 2.2e-16

Ex3: Coefficients and Group Means

Linear Regression and ANOVA

  • For a binary X (Ex2), linear regression can perform a two-sample t-test (equal variance).

  • In a categorical X (Ex3), a Linear regression provides information about the means.

  • If we would like to test whether the categorical variable diagnosis is associated with hippo, we can use either linear regression or analysis of variance (ANOVA).

  • ANOVA is to examine whether the means of different groups are equal. In this case, we want to test whether the mean hippocampal volume is the same for healthy, MCI, and AD groups.

Conduct ANOVA Using Linear Regression

  • Two ways to preform ANOVA using linear regression:
    • Using the lm function to fit the model and then using
Code
alzheimer_data <- read.csv("https://raw.githubusercontent.com/COSMOS-DataScience/slides/refs/heads/main/data/alzheimer_data.csv", head=T) %>% 
  select(id, diagnosis, age, educ, female, height, weight, lhippo, rhippo) %>% mutate(
    diagnosis = factor(diagnosis, levels=c("0","1","2"), labels = c("Healthy", "MCI", "AD")), female = as.factor(female), hippo = lhippo + rhippo)

summary(lm(hippo~diagnosis, data=alzheimer_data))

Call:
lm(formula = hippo ~ diagnosis, data = alzheimer_data)

Residuals:
    Min      1Q  Median      3Q     Max 
-4.5797 -0.5862 -0.0074  0.5770  3.4233 

Coefficients:
             Estimate Std. Error t value Pr(>|t|)    
(Intercept)   6.43207    0.02234  287.97   <2e-16 ***
diagnosisMCI -0.57198    0.04180  -13.68   <2e-16 ***
diagnosisAD  -0.89476    0.04339  -20.62   <2e-16 ***
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Residual standard error: 0.8748 on 2697 degrees of freedom
Multiple R-squared:  0.155, Adjusted R-squared:  0.1544 
F-statistic: 247.3 on 2 and 2697 DF,  p-value: < 2.2e-16
Code
anova(lm(hippo~diagnosis, data=alzheimer_data))
Analysis of Variance Table

Response: hippo
            Df  Sum Sq Mean Sq F value    Pr(>F)    
diagnosis    2  378.56 189.281  247.33 < 2.2e-16 ***
Residuals 2697 2064.01   0.765                      
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Conduct ANOVA Using Linear Regression

  • Two ways to preform ANOVA using linear regression:
    • Using the aov function
Code
alzheimer_data <- read.csv("https://raw.githubusercontent.com/COSMOS-DataScience/slides/refs/heads/main/data/alzheimer_data.csv", head=T) %>% 
  select(id, diagnosis, age, educ, female, height, weight, lhippo, rhippo) %>% mutate(
    diagnosis = factor(diagnosis, levels=c("0","1","2"), labels = c("Healthy", "MCI", "AD")), female = as.factor(female), hippo = lhippo + rhippo)
summary(aov(hippo~diagnosis, data=alzheimer_data))
              Df Sum Sq Mean Sq F value Pr(>F)    
diagnosis      2  378.6  189.28   247.3 <2e-16 ***
Residuals   2697 2064.0    0.77                   
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1

Multiple Linear Regression

Ex4: Motivating Example

  • In Ex 2 we found that healthy men and womean have different hippocampal volume.

  • Men and women are also different in height.

  • Does height explain the difference in hippocampal volume between men and women?

  • We can answer this question using multiple linear regression.

Can the difference be explained by height?

Code
ggplot(alzheimer_healthy_old, aes(x=height, y=hippo, color=female))+geom_point()

The adjusted difference

Code
summary(lm(hippo ~ height + female, data=alzheimer_healthy_old))$coefficients
               Estimate  Std. Error   t value     Pr(>|t|)
(Intercept)  1.80472670 0.469111040  3.847121 1.246078e-04
height       0.07133566 0.006771182 10.535185 4.498807e-25
female1     -0.08743904 0.054060094 -1.617442 1.059967e-01
  • The adjusted difference between men and women

    • has a much smaller difference
    • is less significant

Interpret the Coefficients in a multiple regression

  • In this multiple regression, the fitted model is \[y=1.805 + 0.071 *height - 0.087 *female\]

  • How to interpret the coefficients?

  • The model we fit gives two parallel fitted lines, i.e., men and women have the same slope but different intercepts.

    • men: y=1.805 + 0.071 *height
    • women: y=(1.805- 0.087) + 0.071 *height

Interpret the Coefficient of female

  • The slope -0.087 is the estimated difference between women and men with the same height.
Code
# Fit additive model
fit <- lm(hippo ~ height + female, data = alzheimer_healthy_old)

# Create prediction grid
newdat <- expand.grid(
  height = seq(min(alzheimer_healthy_old$height),
               max(alzheimer_healthy_old$height),
               length.out = 100),
  female = levels(alzheimer_healthy_old$female)
)

newdat$pred <- predict(fit, newdata = newdat)

# Plot
ggplot(alzheimer_healthy_old,
       aes(x = height, y = hippo, color = female)) +
  geom_point(alpha = 0.6) +
  geom_line(data = newdat,
            aes(y = pred),
            linewidth = 1.2) +
  labs(
    x = "Height (cm)",
    y = "Hippocampal Volume",
    color = "Gender",
    title = "hippo ~ height + female"
  ) +
  theme_minimal()

Summarize a Linear Model

Code
lm(hippo ~ height + female, data = alzheimer_healthy_old)%>%summary()%>%coefficients
               Estimate  Std. Error   t value     Pr(>|t|)
(Intercept)  1.80472670 0.469111040  3.847121 1.246078e-04
height       0.07133566 0.006771182 10.535185 4.498807e-25
female1     -0.08743904 0.054060094 -1.617442 1.059967e-01
               Estimate  Std. Error   t value     Pr(>|t|)
(Intercept)  1.80472670 0.469111040  3.847121 1.246078e-04
height       0.07133566 0.006771182 10.535185 4.498807e-25
female1     -0.08743904 0.054060094 -1.617442 1.059967e-01
  • After adjusting for height, women have an estimated hippocampal volume that is 0.087 units lower than men (SE = 0.054; 95% CI: −0.193 to 0.019; P = 0.106), although this difference is not statistically significant.

Interpret the Coefficients

  • Interpretation: Similarly, the slope 0.071 is the estimated increase in hippocampal volume for each in increase in height, holding gender constant.

  • Recall that the fitted model is

\[y=1.805 + 0.071 *height - 0.087 *female\]

  • If we do not change female but increase height by 1 unit, the estimated increase in hippocampal volume is 0.071 cc.

  • After adjusting for sex, each additional in of height is associated with an estimated increase of 0.071 units in hippocampal volume (SE = 0.0068; 95% CI: 0.058 to 0.085; P < 0.001).

When not Forcing Equal Slopes

  • The two lines are nearly parallel, which is consistent with the model we fit.
Code
ggplot(alzheimer_healthy_old, aes(x = height, y = hippo, color = female)) +
  geom_point(alpha = 0.6) +
  geom_smooth(method = "lm", se = FALSE) +
  labs(
    x = "Height (cm)",
    y = "Hippocampal Volume",
    color = "Gender",
    title = "Fitted Lines from hippo ~ height + female"
  ) +
  theme_minimal()

Model Diagnostics and Outliers

  • The typical assumptions of linear regression models are

    • Linearity
    • Independent observations
    • Constant variance and normality of the error term (residuals)
  • The first two assumptions are usually justified by our domain knowledge, our study design, and simple visualization of data.

  • To investigate the validity of the third assumptions we can use diagnostic plots by visualizing the residuals

  • Outliers are points that do not follow the general pattern of the majority of the data. Visualization methods are often used.

Advanced Topics

Advanced Topics

  • Topic 1: Interactions
  • Topic 2: Transform X and Y

Topic 1: Interactions

Introduction to Interactions

  • In Ex 4 we fit a multiple linear regression
Code
summary(lm(hippo ~ height + female, data=alzheimer_healthy_old))$coefficients
               Estimate  Std. Error   t value     Pr(>|t|)
(Intercept)  1.80472670 0.469111040  3.847121 1.246078e-04
height       0.07133566 0.006771182 10.535185 4.498807e-25
female1     -0.08743904 0.054060094 -1.617442 1.059967e-01
  • There are two fitted lines
    • men: y=1.805 + 0.071 *height
    • women: y=(1.805- 0.087) + 0.071 *height

Interactions: Introduction

  • The two fitted lines in Ex4 are parallel to each other.

  • This is because hippo ~ height + female implies an additive effect between gender and height. In other words, the effect of height does not depend on gender.

  • When suspecting that the effect of one explanatory variable on the response may depend on another explanatory variable, we can include an interaction term in the model.

Ex 5: The Joint Effects of Age and Gender on Hippocampal Volume

  • In this example, we will examine how age and gender jointly affect hippocampal volume.

  • In particular, we will assess whether the effect of age on hippocampal volume may depend on gender.

Ex 5: Two Separate Lines

  • If we fit two separate lines, do they seem to have the same slope?
Code
ggplot(alzheimer_healthy_old, aes(x=age, y=hippo, color=female))+
  geom_point()+
  geom_smooth(method=lm, se=F)

Ex 5: A Model with Interactions

  • Let y be hippocampal volume
  • Example: \[y=\beta_0 + \beta_{age} age + \beta_f f + \beta_{age\times f} age\times f + \epsilon\] where \(f\) means female.
  • In R, the syntax is one of the two equivalent ways:
    • hippo ~ age + female + age:female
    • hippo ~ age * female
Code
summary(lm(hippo~ age*female, data=alzheimer_healthy_old))$coefficients
                Estimate  Std. Error    t value      Pr(>|t|)
(Intercept)  9.182369560 0.210806589  43.558266 3.789072e-267
age         -0.035269930 0.003008468 -11.723553  2.059224e-30
female1     -1.041026159 0.255296507  -4.077714  4.790840e-05
age:female1  0.007708627 0.003656786   2.108034  3.519639e-02

The Fitted Lines

  • What are the two fitted lines?

  • Female: \(\hat \beta_0 + \hat \beta_{age} age + \hat \beta_f \times 1 + \hat\beta_{age\times f} (age\times 1)\), which can be rewritten to:

\[(\hat \beta_0 + \hat \beta_f) + (\hat \beta_{age} + \hat\beta_{age\times f}) age.\]

  • Male, similarly, the fitted line is \[\hat \beta_0 + \hat \beta_{age} age \]

The Interaction Coefficient

  • The two groups are parallele if and only fi \(\hat\beta_{age\times f} = 0\).

  • In other words, \(\hat\beta_{age\times f}\) is the estimated difference in the slope of age for females vs for males.

  • Back to the problem, do men and women shrink brain in the same speed?

Interpret Interactions

Code
summary(lm(hippo~ age*female, data=alzheimer_healthy_old))$coefficients
                Estimate  Std. Error    t value      Pr(>|t|)
(Intercept)  9.182369560 0.210806589  43.558266 3.789072e-267
age         -0.035269930 0.003008468 -11.723553  2.059224e-30
female1     -1.041026159 0.255296507  -4.077714  4.790840e-05
age:female1  0.007708627 0.003656786   2.108034  3.519639e-02
  • The difference in brain shrinking speed between men and women is 0.0077cc per year with SE=0.004. The difference is is statistically significant at significance level 0.05.

Interpret Interactions

  • The estimated brain shrinking speed for men is 0.035cc per year.

  • The estimated brain shrinking speed for women is \(|-0.035+0.0077|\approx 0.0273\)cc per year.

Advanced Topic 2: Transform \(X\) and \(Y\)

Transform \(X\)

  • Weight is a little bit skewed. Regress hippocampus volume on log(weight). How to interpret the results?
Code
#plot(log(alzheimer_healthy_old$weight), alzheimer_healthy_old$hippo, xlab="weight", ylab="log(weight)")
summary(lm(hippo~log(weight), data=alzheimer_healthy_old))$coefficients
            Estimate Std. Error  t value     Pr(>|t|)
(Intercept) 1.214054 0.46579899  2.60639 9.242282e-03
log(weight) 1.019022 0.09111367 11.18407 6.237857e-28

Transform \(X\)

Model: \(y=\beta_0 + \beta_1 log(x) + \epsilon\)

  • The estimated change in \(y\) when \(log(x)\) increases by 1 is \(b_1=1.013243\)

  • Increase \(log(x)\) by 1 means:

    • \(log(x)+1=log(x)+log(e)=log(ex)\), which means \(x\) (weight) increases to \(ex\).

    • Equivalently, \(x\) increases by \[\frac{ex-x}{x}=e-1 \approx 1.72 = 172\%.\]

Transform \(X\)

  • Often, we are interested in the estimated change in \(y\) for for a \(p\%\) increase in \(x\).

  • A \(p\%\) increase in x changes \(log(x)\) by \(log((1+p/100)x)=log(x)+log(1+p/100)\).

  • Therefore, the estimated change in \(y\) is is

\[b_1*log(1+p/100).\]

Transform \(Y\)

  • Model: \(log(y)=\beta_0 + \beta_1 x + \epsilon\)

  • Now the response is on the log scale.

  • A one-unit increase in x increases the expected value of \(log(y)\) by \(b_1\), i.e., from \(log(y_0)\) to \(log(y_1)=log(y_0)+b_1\).

  • Back to the original scale, \[y_1=e^{log(y_1)}=e^{log(y_0)+b_1}=e^{b_1}*y_0\]

Code
#plot(alzheimer_healthy_old$height, log(alzheimer_healthy_old$weight), xlab="height", ylab="log(weight)")
summary(lm(log(weight)~height, data=alzheimer_healthy_old))$coefficients
             Estimate  Std. Error  t value      Pr(>|t|)
(Intercept) 3.1652744 0.080729831 39.20824 4.708633e-231
height      0.0296628 0.001230638 24.10360 1.591322e-108
  • In this example, \(b_1=0.02935588\).

  • When increase \(x\) (age) by 1 unit, the expected value of \(log(y)\) (log(weight)) increases by 0.02935588.

  • Back to the original scale, \(y_1=e^{log(y_1)}=e^{log(y_0)+b_1}=e^{b_1}*y_0=e^{0.02935588}*y_0\approx 1.0298*y_0\).

  • Or, equivalently, the expected value of \(y\) (weight) increases by \(2.98\%\) for each additional year of age.