简体   繁体   English

ggplot R中的for循环中的图形编号

[英]ggplot figure number in for loop in R

I have got the following data: 我有以下数据:

    Detector=c("A", "A", "A", "A","B", "B", "B", "B","C", "C", "C", "C")
    hours=rep(c(0,4,24,48),3)
    LoD=c(rep(25,4),rep(40,4),rep(34,4))
    Ct=c(24,24.2,24.3,24,43,42,43,41,35,37,35,35.6)
    Sample.Type=c(rep("T",2),rep("P",4),rep("T",5), rep("P",1))
    d4.1=data.frame(Detector,hours, Ct, LoD, Sample.Type)

I want to plot Ct vs hours as a simple scatterplot, as a loop for each Detector, and show each detector's lod value as a horizontal line on the plot. 我想将Ct与小时数作图作为一个简单的散点图,作为每个检测器的循环,并将每个检测器的lod值显示为绘图上的水平线。 I use the following code which works perfectly well: 我使用以下代码,效果很好:

    for(i in unique(d4.1$Detector)) {
    print(ggplot(d4.1[d4.1$Detector==i], aes(d4.1$hours[d4.1$Detector==i], 
    d4.1$Ct[d4.1$Detector==i], colour = d4.1$Sample.Type[d4.1$Detector==i]))+
    geom_point()+
    geom_hline(yintercept=mean(d4.1$LoD[d4.1$Detector==i]))+
    ggtitle(paste("Figure", j,i, sep=" "))+
    theme(plot.title = element_text(hjust = 
    0.5),plot.caption=element_text(hjust = 0))+
    labs(x="Hours/Time Points", y="Ct",caption=paste("The solid black line 
    is the LoD(=",mean(d4.1$LoD[d4.1$Detector==i]),") for",i,sep=" "), 
    colour="Sample Types"))}

What I need help with is the ggplot's titles. 我需要的是ggplot的标题。 Each of the plots generated is labeled with A,B and C but i'd like to add the following text to it: 生成的每个图都用A,B和C标记,但我想在其中添加以下文本:

    Figure 1: A
    Figure 2: B
    Figure 3: C

I tried adding a "j" sequence of 1-3 and paste it in title (below) which didnt work. 我尝试添加1-3的“ j”序列,并将其粘贴到标题(如下)中,但此方法无效。 It gave me 9 plots (Figure 1 A,Figure 1 B, Figure 1 C, Figure 2 A...etc) 它给了我9个图(图1A,图1B,图1C,图2A ...等)

     for(i in unique(d4.1$Detector)){for (j in seq(1:3)){print(ggplot(d4.1[which(d4.1$Detector==i),], aes(hours,Ct, colour = Sample.Type))+geom_point()+geom_hline(yintercept=mean(LoD))+ggtitle(paste("Figure",j,i,sep=" "))+theme(plot.title = element_text(hjust = 0.5),plot.caption=element_text(hjust = 0))+labs(x="Hours/Time Points", y="Ct",caption=paste("The solid black line is the LoD(=",mean(LoD),") for",i,sep=" "), colour="Sample Types"))}}

How do I add a sequence of numbers (1,2,3...) to ggplot titles in a loop? 如何在循环中向ggplot标题添加数字序列(1,2,3 ...)? Thank you very much. 非常感谢你。

If you store unique Detector in a variable ( detectors ) and use seq_along you will get indexes 1 to 3 ( x in the function). 如果您存储唯一的Detector在一个变量( detectors ),并使用seq_along你会得到索引为1到3( x的功能)。 You can then create your three plots like this: 然后,您可以创建三个图,如下所示:

detectors <- unique(d4.1$Detector)
lapply(seq_along(detectors), function (x) {
  selected_detector <- detectors[[x]]
  df_plot <- d4.1[d4.1$Detector == selected_detector, ]
  p <- ggplot(df_plot, aes(x = hours, y = Ct, colour = Sample.Type)) +
      geom_point() + geom_hline(yintercept = mean(df_plot$LoD)) +
      ggtitle(paste("Figure", x, selected_detector, sep = " ")) +
      theme(plot.title = element_text(hjust = 0.5),
        plot.caption = element_text(hjust = 0))+
        labs(x = "Hours/Time Points", y = "Ct",
          caption=paste("The solid black line is the LoD(=",
            mean(df_plot$LoD),") for", selected_detector, sep=" "),
          colour="Sample Types")
  print(p)
})

在此处输入图片说明

Since your code is not reproducible, I'd decided to give an alternate example using the iris data. 由于您的代码不可复制,因此我决定使用光圈数据给出一个替代示例。

(i) split iris into a list of 3 subset, based on Species. (i)根据种类将虹膜分为3个子集的列表。 This is similar to d4.1[d4.1$Detector==i,] in the code provided 类似于提供的代码中的d4.1[d4.1$Detector==i,]

df <- split(iris, iris$Species)

(ii) write a generic plot function that takes in different subset (ii)编写一个包含不同子集的通用绘图函数

plotFn <- function(df){
              ggplot(df, aes(Sepal.Length, Petal.Length)) + 
              geom_point() + 
              geom_hline(yintercept = mean(df[,"Petal.Length"]))
          }

(iii) get the list of ggplot object and then do a lapply to individually add in the Figure x: y format. (iii)获取ggplot对象的列表,然后进行lapply来单独添加Figure x: y格式。

p <- lapply(df, plotFn)

lapply(1:length(p), function(x){
          p[[x]] + 
          ggtitle(paste0("Figure ", x, ": ", names(p)[x]))
       })

This will provide three plots: 这将提供三个情节:

在此处输入图片说明

Your code was not reproducible because the way you programmed your loop. 您的代码不可复制,因为您编写循环的方式。 You subset the dataframe first and then within your aes() ask for subsets that no longer exists. 您首先对数据框进行子集设置,然后在aes()中请求不再存在的子集。

Although I find Kristoffer's and Adam's answers more elegant than mine here is a crude version that uses your original loop. 尽管我发现Kristoffer和Adam的答案比我的答案更为优雅,但这里还是一个粗略的版本,它使用了您的原始循环。 I use the fact that factor level A corresponds to the first level, by converting the factor to a numeric. 我通过将因子转换为数字来使用因子级别A对应于第一级别的事实。

for(i in unique(d4.1$Detector)) {


 print(ggplot(d4.1[d4.1$Detector==i,], aes(hours, 
                                           Ct, colour = Sample.Type))+
          geom_point()+
          geom_hline(yintercept=mean(d4.1$LoD[d4.1$Detector==i]))+
          ggtitle(paste("Figure", as.numeric(d4.1$Detector[d4.1$Detector==i]), ":" , i, sep=" "))+
            theme(plot.title = element_text(hjust = 
                                            0.5),plot.caption=element_text(hjust = 0))+
          labs(x="Hours/Time Points", y="Ct",caption=paste("The solid black line 
                                                           is the LoD(=",mean(d4.1$LoD[d4.1$Detector==i]),") for",i,sep=" "), 
               colour="Sample Types"))}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM