使用for循环的多个函数和ggplots

时间:2020-06-09 19:21:59

标签: r function for-loop ggplot2 nested-loops

我想使用ggplot生成许多线性回归图(细菌OTU对温度作图)。我希望曲线图的标题是线性回归方程,由函数确定。当我分别绘制图时,代码起作用,但是当我使用for循环时,代码不起作用。

我一直收到以下错误:

Error in model.frame.default(formula = taxa_list[i] ~ Temperature, data = dataframe,  : 
  variable lengths differ (found for 'Temperature')

请参阅下面的代码。我是否需要嵌套的for循环才能使它正常工作?

taxa_list <- c("Vibrio","Salmonella","Campylobacter","Listeria","Streptococcus","Legionella")
taxa_list <- sort(taxa_list)

for (i in seq_along(taxa_list)) {

  lm_eqn <- function(dataframe) {
    m <- lm(taxa_list[i] ~ Temperature, dataframe)
    p <- summary(m)
    eq <- substitute(italic(y) == a + b %.% italic(x)*","~~italic(r)^2~"="~r2 %.% italic(x)*","~~italic(p)~"="~p0, 
                     list(a = format(unname(coef(m)[1]), digits = 2),
                          b = format(unname(coef(m)[2]), digits = 2),
                          r2 = format(summary(m)$r.squared, digits = 3), 
                          p0 = format(p$coefficients[8], digits = 3)))
    as.expression(eq);
  }

    plot <- ggplot(data = all_data, aes(x = Temperature, y = taxa_list[i], fill = taxa_list[i])) + 
            geom_point(data = all_data, aes(x = Temperature, y = taxa_list[i]), color = "black", size = 3) +
            geom_smooth(method = "lm", size = 1, color = "black", fill = "gray") +
            labs(title = lm_eqn(dataframe = all_data), subtitle = "") + xlab("Temperature") + ylab("Number of OTUs")

    print(plot)

}

1 个答案:

答案 0 :(得分:1)

我试图重写您的代码,以使其更具可读性,效率和可维护性。我使用了tidyverse个选择。我相信您删除的原始* x函数中还有一个额外的eq

library(dplyr)
library(ggplot2)
library(purrr)
library(broom)


taxa_list <- c("Vibrio","Salmonella","Campylobacter","Listeria","Streptococcus","Legionella")
taxa_list <- sort(taxa_list)

MyFunctionNew <- function(data, bacteria, temperature) 
{  
  my_lm <- lm(as.formula(paste(bacteria, "~", temperature)), data = data)
  terms_info <- broom::tidy(my_lm)
  model_info <- broom::glance(my_lm)
  eq <- substitute(italic(y) == a + b %.% italic(x)*","~~italic(r)^2~"="~r2 *","~~italic(p)~"="~p0, 
                   list(a = format(terms_info$estimate[1], digits = 2),
                        b = format(terms_info$estimate[2], digits = 2),
                        r2 = format(model_info$r.squared, digits = 3), 
                        p0 = format(model_info$p.value, digits = 3)))


  plot <- ggplot(data = data, aes_string(x = temperature, y = bacteria, fill = bacteria)) + 
    geom_point(size = 3, show.legend = TRUE) +
    geom_smooth(method = "lm", size = 1, color = "black", fill = "gray") +
    labs(title = eq, subtitle = "") + xlab("Temperature") + ylab("Number of OTUs")

  return(plot)
}

MyFunctionNew(dat1, "Vibrio", "Temperature")
#> `geom_smooth()` using formula 'y ~ x'

purrr::map(taxa_list, ~ MyFunctionNew(dat1, .x, "Temperature"))
#> [[1]]
#> `geom_smooth()` using formula 'y ~ x'

以下是一些组成的数据,它们应该或多或少都足够接近

set.seed(1111)
dat1 <- data.frame(Temperature = runif(200, min = 32, max = 100),
                   Vibrio = rnorm(200),
                   Salmonella = rnorm(200),
                   Campylobacter = rnorm(200),
                   Listeria = rnorm(200),
                   Streptococcus = rnorm(200),
                   Legionella = rnorm(200) 
                   )

相关问题