r中具有不同时间分辨率的堆栈图

时间:2018-08-24 02:30:39

标签: r ggplot2 graph stacked

我正在尝试使用ggplot2和网格排列来堆叠三个图形。所有三个图应具有相同的x轴(但不能共享),问题是它们都具有不同的时间分辨率,而且我很难对齐三个不同图的轴。

这就是我所拥有的:

stacked graphs

我想要类似的东西:

target format

数据集土壤温度

                average
3/1/2018 11:00  9.353692972
3/1/2018 12:00  10.75947564
3/1/2018 13:00  11.56223312
3/1/2018 14:00  11.59511989
3/1/2018 15:00  11.07712308
3/1/2018 16:00  9.762939639
3/1/2018 17:00  7.650089417
3/1/2018 18:00  6.021789611
3/1/2018 19:00  4.844122056
3/1/2018 20:00  3.946675139
3/1/2018 21:00  3.265207733
3/1/2018 22:00  2.751823167
3/1/2018 23:00  2.307551222
3/2/2018 0:00   1.977323322
3/2/2018 1:00   1.714310775
3/2/2018 2:00   1.505199708
3/2/2018 3:00   1.402693267
3/2/2018 4:00   1.384921586
3/2/2018 5:00   1.350009046
....

数据集ppt

3/1/2018    0
3/2/2018    0
3/3/2018    0
3/4/2018    0
3/5/2018    0
3/6/2018    0
3/7/2018    0
3/8/2018    0
3/9/2018    0
3/10/2018   0
3/11/2018   0
3/12/2018   0
3/13/2018   0
3/14/2018   0

数据集通量

DPF     U       N
7.08    0.00    0.00
14      0.01    0.02
22      0.16    0.25
29.21   0.00    0.00
33.88   0.05    0.00
42.08   0.00    0.00

代码

# define sheets
hourly <- read_excel("ashland2_graphs.xlsx", sheet = 'Hourly')
daily <- read_excel("ashland2_graphs.xlsx", sheet = 'Climate')
nh3flux <-read_excel('ashland2_graphs.xlsx', sheet = 'flux')


# define soil temp
soiltemp <- as.numeric(as.character(hourly$average))

# soil temperature graph
# define x axis
x = c(1:length(soiltemp))

fig1 <- ggplot()+
  geom_line(aes(x=x,y = soiltemp), stat = 'identity') +
  scale_x_continuous(breaks = seq(1, length(soiltemp), by = 240), 
                     label = c('0', '10', '20', '30', '40'))

# precipitation graph
ppt <- as.numeric(as.character(daily$ppt))

# precip x axis
x2 = c(1:length(ppt))

fig2 <- ggplot(climate) +
  geom_bar(aes(x = x2, y = ppt), stat = 'identity', color = "grey") +
  scale_y_continuous(expand = c(0, 0))

print(fig2)

# Losses
urea <- as.numeric(as.character(nh3flux$`NH3 Flux g/m2 day-1 - urea`))
nbpt <- as.numeric(as.character(nh3flux$`NH3 Flux g/m2 day-1 - nbpt`))
x3 <- nh3flux$`Days post fertilization`

fig3 <- ggplot(nh3flux) +
  geom_point(mapping = aes(x = x3, y = urea)) +
  geom_line(mapping = aes(x = x3, y = urea)) +
  geom_point(mapping = aes(x = x3, y = nbpt)) +
  geom_line(mapping = aes(x = x3, y = nbpt), linetype = 'dashed') +
  scale_x_continuous(breaks=seq(0, 45, 10), limits = c(0, 45))

print(fig3)

# stack graphs
grid.arrange(fig3, fig2, fig1, ncol = 1)

1 个答案:

答案 0 :(得分:1)

设置

为了易于重现,我将使用mtcars数据集 演示如何解决这个问题。首先,让我们创建三个图:

library(ggplot2)

set.seed(123)
dfs <- split(mtcars, sample(3, nrow(mtcars), replace = TRUE))

# Three plots, with the same x variable but different y and geoms
p1 <- ggplot(dfs[[1]], aes(wt, mpg)) + geom_point()
p2 <- ggplot(dfs[[2]], aes(wt)) + geom_histogram()
p3 <- ggplot(dfs[[3]], aes(wt, cyl)) + geom_smooth()

plots <- list(p1, p2, p3) # easier to work with them all in a list

这是堆积的图,显示出与您同样的问题:

cowplot::plot_grid(plotlist = plots, ncol = 1)
#> `stat_bin()` using `bins = 30`. Pick better value with `binwidth`.
#> `geom_smooth()` using method = 'loess' and formula 'y ~ x'

(我不使用grid.arrange(),因为它缺少我们需要的某些功能 寻找解决方案。)

发现问题

我们可以确定两个需要注意的问题:

  1. 在所有图中,x轴限制必须相等。
  2. 绘图区域需要对齐。 (变化的y轴标签长度会导致 绘图区域的大小会有所不同。)

解决方案

第一个问题可以通过创建单个坐标对象来解决 定义我们想要的x轴限制。通过列表中的图,很容易 使用lapply()将此坐标系应用于每个坐标系:

common_coord <- coord_cartesian(xlim = c(1.5, 5.5))
common_x_plots <- lapply(plots, `+`, common_coord)

对于您的数据,将限制设置为c(0, 45)可以很好地解决问题。

第二个问题比较棘手,我不认为gridExtra::grid.arrange() 不需要很多额外的工作就可以解决它。这就是为什么我会建议 使用 cowplot 包中的plot_grid():它有一个align 我们可以通过添加一些额外的空间来排列绘图区域的选项 轴标题和轴标签之间的位置。

结果

解决了两个问题后,结果如下:

cowplot::plot_grid(plotlist = common_x_plots, ncol = 1, align = "v")
#> `stat_bin()` using `bins = 30`. Pick better value with `binwidth`.
#> `geom_smooth()` using method = 'loess' and formula 'y ~ x'

采用这种方法,您也应该可以使用真实数据来实现所需的功能。

reprex package(v0.2.0.9000)于2018-08-24创建。