如何在mutate语句中使用过滤器?

时间:2019-03-16 06:43:59

标签: r dplyr

我想计算与特定日期的公司列表相关的投资。我有公司列表以及投资日期。

这是我的数据-

参考日期

d1 <- as.Date(paste0("201001","01"), "%Y%m%d")
d2 <- as.Date(paste0("201201","01"), "%Y%m%d")
dat <- seq(d1,d2,by="month")

投资数据

> head(df)
        company_name funding_round_type funding_round_code  funded_at raised_amount_usd  yearMonth
1            0-6.com            venture                  A 2008-03-19           2000000 2008-03-01
2   004 Technologies            venture                    2014-07-24                NA 2014-03-01
3 01Games Technology        undisclosed                    2014-07-01             41250 2014-03-01
4             H2O.ai            venture                  B 2015-11-09          20000000 2015-03-01
5             H2O.ai               seed                    2013-05-22           3000000 2013-03-01
6             H2O.ai            venture                    2013-01-03           1700000 2013-03-01
  

我想计算在dat中每个日期的时间每个公司筹集了多少资金。

result <- merge(dat, df$company_name) %>% 
  mutate(asOf = x,
         companyName = as.character(y)) %>% select(-x, -y) %>%
  mutate(raised = sum(df[df$company_name == companyName & 
                                      df$yearMonth < asOf,c("raised_amount_usd")])) 

很遗憾,该过滤器无法正常工作。如果我将其设置为特定公司,则可以使用。例如,此方法有效:sum(df[df$company_name == companyName & df$yearMonth < asOf,c("raised_amount_usd")])

我想要一个看起来像这样的结果-

        asOf                      companyName            cumulative_raised
1            2010-01-01            0-6.com                  0
2            2010-02-01            0-6.com                  12000000
3            2010-03-01            0-6.com                  12000000
4            2010-01-01            H2O.ai                   0
5            2010-02-01            H2O.ai                   5000000
6            2010-03-01            H2O.ai                   9300000

当它位于mutate子句中时,如何使它起作用?

1 个答案:

答案 0 :(得分:1)

解决此问题的一种方法是将complete(来自tidyr)与group_bymutatesummarize(来自dplyr)一起使用以及cumsum而非sum(以R为基础)。 由于您提供的数据几乎与所需的时间间隔重叠,因此我对时间间隔进行了一些修改以显示其工作原理。当然,这是完全灵活的,您可以使用任意间隔:

library(dplyr)
library(tidyr)

my.dat <- seq(as.Date("2013-03-01"), as.Date("2014-04-01"), by = "month")

new.df <- my.df %>% 
  complete(company_name, yearMonth = my.dat, fill = list(raised_amount_usd = 0)) %>% 
  group_by(company_name, yearMonth) %>% 
  summarize(raised_amount_usd = sum(raised_amount_usd, na.rm = TRUE)) %>% 
  arrange(yearMonth) %>% 
  mutate(cumulative_raised = cumsum(raised_amount_usd)) %>% 
  select(company_name, yearMonth, cumulative_raised) 

tail(new.df, 10)

# A tibble: 10 x 3
# Groups:   company_name [4]
   company_name       yearMonth  cumulative_raised
   <chr>              <date>                 <dbl>
 1 01Games Technology 2014-02-01                 0
 2 H2O.ai             2014-02-01           4700000
 3 0-6.com            2014-03-01                 0
 4 004 Technologies   2014-03-01                 0
 5 01Games Technology 2014-03-01             41250
 6 H2O.ai             2014-03-01           4700000
 7 0-6.com            2014-04-01                 0
 8 004 Technologies   2014-04-01                 0
 9 01Games Technology 2014-04-01             41250
10 H2O.ai             2014-04-01           4700000

它如何工作?

首先,使用completeyearMonth栏中填写缺少的日期,并排除不在指定时间范围内的日期。然后,使用group_by组成company_nameyearMonth的组,然后分别为每个日期和公司summarize raised_amount_usd组(以汇总在与H2O.ai的日期相同,即2013年3月1日)。然后,我们按yearMonth排列数据并计算累计和。数据仍按company_name分组,因此计算出每个公司的累计金额。最后,我们只选择您感兴趣的列。

数据

my.df <- 
  structure(list(company_name = c("0-6.com", "004 Technologies", "01Games Technology", "H2O.ai", "H2O.ai", "H2O.ai"), 
                 funding_round_type = c("venture", "venture", "undisclosed", "venture", "seed", "venture"), 
                 funding_round_code = c("A", " ", " ", "B", " ", " "), 
                 funded_at = structure(c(13957, 16275, 16252, 16748, 15847, 15708), class = "Date"), 
                 raised_amount_usd = c(2000000L, NA, 41250L, 20000000L, 3000000L, 1700000L), 
                 yearMonth = structure(c(13939, 16130, 16130, 16495, 15765, 15765), class = "Date")), 
            class = "data.frame", row.names = c(NA, -6L))