在R中的一个图中针对单个列绘制多个列

时间:2016-01-21 21:18:58

标签: r plot

我有一个包含9列的数据框,包括经过时间(天)的列:

Probes <- data.frame(Days=seq(0.01, 4.91, 0.01), DJ1=-45:445, SJ2=-50:440, SJ3=10:500, SJ4=-200:290, DJ2=-150:340, DJ9=100:590, SJ21=-300:190, SJ32=-100:390) 

我想在一个图上创建一个包含多个系列的折线图。我将绘制数据框中剩余列的第一列与第一列(天)。

我知道执行此操作的基本代码...但是,我想知道是否有一个更简单的选项,当您想要将数据框中的所有列映射到一列时,正如我现在所做的那样。为每个列名称键入一行代码似乎是多余的,特别是因为我必须在50多个数据帧上进行此操作。

对于我的特定数据集,我想用&#34; S&#34;在标题中&#34; brown&#34;以及&#34; D&#34;在标题中显示为橙色。

我为此编写了长而笨重的代码,以便您可以看到我要输出的输出。有没有更简单的方法(也许在ggplot中)?

png("ProbesPlot.png", height = 1000, width = 1400, units = "px", res = 200)
par(xpd=T, mar=par()$mar+c(0,0,0,6))
plot(Probes$Days, Probes$DJ1, type="l", lwd=2, lty=1, col="orange", main="Depth in Sediments- 4.5 cm", xlab="Elapsed Time (days)", ylab="Eh (mV)", xlim=c(0, 8), ylim=c(-400,600), bty="n") 
lines(Probes$Days, Probes$SJ2, type="l", lwd=2, lty=1, col="brown")
lines(Probes$Days, Probes$SJ3, type="l", lwd=2, lty=1, col="brown")
lines(Probes$Days, Probes$SJ4, type="l", lwd=2, lty=1, col="brown")
lines(Probes$Days, Probes$DJ2, type="l", lwd=2, lty=1, col="orange ")
lines(Probes$Days, Probes$DJ9, type="l", lwd=2, lty=1, col="orange ")
lines(Probes$Days, Probes$SJ21, type="l", lwd=2, lty=1, col="brown")
lines(Probes$Days, Probes$SJ32, type="l", lwd=2, lty=1, col="brown")
legend(8.5,400, c("4 cm", "1 cm"), lty=c(1,1),  lwd=c(2,2), col=c("orange", " brown"), bty="n", title="Depth") 
dev.off() 

3/1编辑问题@ eipi10我有一个包含29列的额外数据框,包括经过时间(天)的列。我想创建相同类型的绘图,但我现在有3个(D,M和S),而不是2个颜色类别(D和S)。这是我的新数据框结构的一个例子:

Probes <- data.frame(Days=seq(0.01, 4.91, 0.01), B1D.J1=-45:445, B1S.J2=-50:440, B1M.J3=10:500, B1S.J4=-200:290, B1D.J25=-150:340, B1D.J9=100:590, B1S.J21=-300:190, B1S.J32=-100:390, B1D.J18=-15:475, B1M.J22=-70:420, B1M.J31=5:495, B1S.J43=-200:290, B1D.J27=-150:340, B1D.J99=100:590, B1S.J87=-300:190, B1S.J65=-100:390, B1S.J44=-300:190, B1M.J90=-100:390, B1D.J18=-15:475, B1M.J26=-70:420, B1M.J66=5:495, B1M.J43=-200:290, B1D.J52=-150:340, B1D.J96=-50:440, B1M.J53=-300:190, B1M.J74=-100:390)

此外,我唯一需要的唯一传奇是区分颜色的小传说:橙色=深色,棕色=中度,红色=浅色(D,M和S)

2 个答案:

答案 0 :(得分:3)

根据@MikeWise的建议,您可以通过ggplot2了解如何轻松实现这一目标:

library(ggplot2)
library(reshape2)
library(dplyr)

Probes <- data.frame(Days=seq(0.01, 4.91, 0.01), DJ1=-45:445, SJ2=-50:440, SJ3=10:500, SJ4=-200:290, DJ2=-150:340, DJ9=100:590, SJ21=-300:190, SJ32=-100:390) 

# Convert data to long format
Probes.m = melt(Probes, id.var="Days")

# Reorder factor levels so "D's" and "S's" are grouped together
Probes.m$variable = factor(Probes.m$variable, 
                           levels=sort(unique(as.character(Probes.m$variable))))

ggplot(Probes.m, aes(Days, value, colour=variable)) +
  geom_line() +
  scale_colour_manual(values=rep(c("orange","brown"), c(3,5))) +
  guides(colour=FALSE) +
  geom_text(data=Probes.m %>% group_by(variable) %>% filter(value==max(value)),
            aes(label=variable, x=Days + 0.1, y=value), size=3, hjust=0) +
  labs(x="x-label", y="y-label") +
  ggtitle("My Title")

enter image description here

更新:根据您提供的评论和更新后的数据,问题在于您的许多行完全重叠,因此他们会在另一行之间绘制一个。您可以通过检查样本数据来查看。此外,使用您的新数据并使用geom_text_repel代替geom_text,您可以看到有多个标签用于&#34;相同&#34; line,实际上只是具有不同名称的同一行的多个副本。

ggplot(Probes.m, aes(Days, value, colour=variable)) +
  geom_line() +
  scale_colour_manual(values=rep(c("orange","brown","red"), c(9,9,8))) +
  guides(colour=FALSE) +
  geom_text_repel(data=Probes.m %>% group_by(variable) %>% filter(value==max(value)),
            aes(label=variable, x=Days + 0.1, y=value), size=3) +
  labs(x="x-label", y="y-label") +
  ggtitle("My Title")

enter image description here

答案 1 :(得分:1)

根据@ eipi10的回答,为了应对重叠的文字,你可以使用一个新的包ggrepel,它提供了一个新的&#39; geom&#39;为ggplot。 [我之前使用tidyr而不是reshape2开始回答这个问题,并且没有声誉可以发表评论,所以将此作为新答案发布]

library(ggplot2)
library(tidyr)
library(dplyr)
library(ggrepel)

Probes <- data.frame(Days=seq(0.01, 4.91, 0.01), DJ1=-45:445, SJ2=-50:440, SJ3=10:500, SJ4=-200:290, DJ2=-150:340, DJ9=100:590, SJ21=-300:190, SJ32=-100:390)

tidiedProbes <-
  Probes %>%
  tidyr::gather(key = probeRef, value = `Eh (mV)`, - Days) %>%
  dplyr::mutate(lineColour = ifelse(substring(probeRef, 1, 1) == "D", "D", "S"))

dataForLabels <-
  tidiedProbes %>%
  filter(Days == max(Days))

newPlot <- 
  tidiedProbes %>%
  ggplot() +
  geom_line(aes(x = Days, y = `Eh (mV)`, colour = lineColour, group = probeRef)) + 
  scale_color_manual(values = c("orange", "brown")) +
  geom_text_repel(
      data = dataForLabels, 
      aes(x = Days, y = `Eh (mV)`, label = probeRef)) +
  ggtitle("Depth in Sediments - 4.5 cm") + 
  xlab("Elapsed Time (days)") +
  theme(legend.title = element_blank())
newPlot

Don't have reputation for posting images yet but hopefully plot looks as expected