计算数据框中多个范围的汇总统计信息

时间:2018-03-05 21:49:05

标签: r loops dplyr

我有一个大型数据框“table”:

  Year Month        Model Scenario Longitude Latitude tas_month pr_month
1 2000     1 ccsm4_r1i1p1    rpc45      9.57   -84.53     24.20    40.63
2 2000     2 ccsm4_r1i1p1    rpc45      9.57   -84.53     25.05    54.20
3 2000     3 ccsm4_r1i1p1    rpc45      9.57   -84.53     25.19    36.87
4 2000     4 ccsm4_r1i1p1    rpc45      9.57   -84.53     25.44   126.47
5 2000     5 ccsm4_r1i1p1    rpc45      9.57   -84.53     25.36   282.44
6 2000     6 ccsm4_r1i1p1    rpc45      9.57   -84.53     25.71   284.68

我想使用mean(tas_month)创建一个新的数据框,每个期限为五年,mean(pr_month)group_by(Month, Longitude, Latitude, Model, Scenario) Period Month Model Scenario Longitude Latitude tas_month pr_month 1 1 1 ccsm4_r1i1p1 rpc45 9.57 -84.53 24.20 40.63 2 2 2 ccsm4_r1i1p1 rpc45 9.57 -84.53 25.05 54.20 3 3 3 ccsm4_r1i1p1 rpc45 9.57 -84.53 25.19 36.87 4 4 4 ccsm4_r1i1p1 rpc45 9.57 -84.53 25.44 126.47 5 5 5 ccsm4_r1i1p1 rpc45 9.57 -84.53 25.36 282.44 6 6 6 ccsm4_r1i1p1 rpc45 9.57 -84.53 25.71 284.68 。此新数据框还必须有一个新列,其中每一行都具有这些值所属的5年期间的值。

fiveyears <- seq(2000, 2100, 5)

我已经创建了一个五年的矢量:

for (i in seq_along(fiveyears)){
  table %>% filter(Year < (i+5) & Year >= i) %>% 
  group_by(Month, Longitude, Latitude, Model, Scenario) %>% 
  summarise(pr_month = mean(pr_month), tas_month = mean(tas_month))

但仍然无法弄清楚如何计算手段。我在考虑像这个“伪”代码,但它仍然非常粗糙:

<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">
...
    <application xmlns="urn:schemas-microsoft-com:asm.v3">
        <windowsSettings>
            <dpiAware xmlns="http://schemas.microsoft.com/SMI/2005/WindowsSettings">true</dpiAware>
     <dpiAwareness xmlns="http://schemas.microsoft.com/SMI/2016/WindowsSettings">
         PerMonitor
</dpiAwareness> </windowsSettings> </application> ... </assembly>

非常感谢任何帮助。

2 个答案:

答案 0 :(得分:2)

您的示例数据仅涉及2000年,因此我们可以使用以下内容:

df <- data.frame(Year = rep(2000:2011, each = 3), x = rnorm(36))

你的想法很好,但我们可以让它更简洁:

df %>% group_by(Year %/% 5) %>% summarize(y = mean(x))
# A tibble: 3 x 2
#   `Year%/%5`      y
#        <dbl>  <dbl>
# 1        400  0.334
# 2        401  0.116
# 3        402 -0.222

其中%/%表示整数除法。如果需要,您可以更改第一列名称并相应地标准化其值。

更新

df %>% group_by(Year %/% 5, Month, Longitude, Latitude, Model, Scenario) %>% 
  summarize(tas_month = mean(tas_month), pr_month = mean(pr_month)) %>% 
  rename("Period" = `Year%/%5`) %>% 
  transform(Period = Period - min(df$Year %/% 5) + 1)
#   Period Month Longitude Latitude        Model Scenario tas_month pr_month
# 1      1     1      9.57   -84.53 ccsm4_r1i1p1    rpc45     24.20    40.63
# 2      1     2      9.57   -84.53 ccsm4_r1i1p1    rpc45     25.05    54.20
# 3      1     3      9.57   -84.53 ccsm4_r1i1p1    rpc45     25.19    36.87
# 4      1     4      9.57   -84.53 ccsm4_r1i1p1    rpc45     25.44   126.47
# 5      1     5      9.57   -84.53 ccsm4_r1i1p1    rpc45     25.36   282.44
# 6      1     6      9.57   -84.53 ccsm4_r1i1p1    rpc45     25.71   284.68

答案 1 :(得分:0)

根据@Julius的建议,我最终得到了这个。不像我想的那样干净或优雅,但至少我希望它可以给有类似问题的人提供一些想法:

tbl_month_5years <- table %>% 
  group_by(Year %/% 5, Month, Longitude, Latitude, Model, Scenario) %>%
  summarise(tas_mean = mean(tas_month), pr_mean = mean(pr_month)) %>%
  rename(period = `Year%/%5`)

periods_5years <- tbl_month_5years %>% group_by(period) %>%    
  summarise(n())

years5 <- as.data.frame(seq(2000, 2095, 5))
years5 <-years5 %>% rename(ini_year = `seq(2000, 2095, 5)`)
years5 <- cbind(years5, periods_5years)

tbl_month_5years <- tbl_month_5years %>% 
  left_join(years5, by = "period") %>% select(-`n()`)