Here's a solution using tidyverse packages.
The key is the broom package, whcih simplifies the process of extracting model data. For example:
fit1 <- lm(mpg ~ cyl, data = mtcars) summary(fit1) fit1 %>% tidy() %>% select(estimate, term)
Result
# A tibble: 2 x 2 estimate term <dbl> <chr> 1 37.9 (Intercept) 2 -2.88 cyl
I wrote a function to extract and format the information using dplyr:
get_formula <- function(object) { object %>% tidy() %>% mutate( term = if_else(term == "(Intercept)", "", term), sign = case_when( term == "" ~ "", estimate < 0 ~ "-", estimate >= 0 ~ "+" ), estimate = as.character(round(abs(estimate), digits = 2)), term = if_else(term == "", paste(sign, estimate), paste(sign, estimate, term)) ) %>% summarize(terms = paste(term, collapse = " ")) %>% pull(terms) } get_formula(fit1)
Result
[1] " 37.88 - 2.88 cyl"
Then use ggplot2 to plot the line and add a caption
mtcars %>% ggplot(mapping = aes(x = cyl, y = mpg)) + geom_point() + geom_smooth(formula = y ~ x, method = "lm", se = FALSE) + labs( x = "Cylinders", y = "Miles per Gallon", caption = paste("mpg =", get_formula(fit1)) )
Plot using geom_smooth()
This approach of plotting a line really only makes sense to visualize the relationship between two variables. As @Glen_b pointed out in the comment, the slope we get from modelling mpg as a function of cyl (-2.88) doesn't match the slope we get from modelling mpg as a function of cyl and other variables (-1.29). For example:
fit2 <- lm(mpg ~ cyl + disp + wt + hp, data = mtcars) summary(fit2) fit2 %>% tidy() %>% select(estimate, term)
Result
# A tibble: 5 x 2 estimate term <dbl> <chr> 1 40.8 (Intercept) 2 -1.29 cyl 3 0.0116 disp 4 -3.85 wt 5 -0.0205 hp
That said, if you want to accurately plot the regression line for a model that includes variables that don't appear included in the plot, use geom_abline() instead and get the slope and intercept using broom package functions. As far as I know geom_smooth() formulas can't reference variables that aren't already mapped as aesthetics.
mtcars %>% ggplot(mapping = aes(x = cyl, y = mpg)) + geom_point() + geom_abline( slope = fit2 %>% tidy() %>% filter(term == "cyl") %>% pull(estimate), intercept = fit2 %>% tidy() %>% filter(term == "(Intercept)") %>% pull(estimate), color = "blue" ) + labs( x = "Cylinders", y = "Miles per Gallon", caption = paste("mpg =", get_formula(fit2)) )
Plot using geom_abline()
y = m x1 + b x2 + c? 2) The line you plotted (1 predictor) doesn't correspond to the linear model you fitted. Indeed, the coefficient for the cost variable in the straight line fit could be different in sign to the one from the multiple regression. If you print something that could be drastically different, won't that be confusing?