如何使用for循环计算每个唯一id自上个月购买以来的月数?

如何使用for循环计算每个唯一id自上个月购买以来的月数?,r,for-loop,R,For Loop,我想计算自上个月购买以来的月数。 我的dataframe是这样的: new_df <- months_since_last_purchase(df) df 每月购买的id 1 1 3 1 2 0 1 3 0 1 4 1 2 1 1 2 2 0 2 3 3 2 4 1 省略100行 我想使用for循环获得如下数据帧: new_df <- months_since_last_purchase(df) i

我想计算自上个月购买以来的月数。 我的
dataframe
是这样的:

new_df <- months_since_last_purchase(df)
df
每月购买的id
1  1     3
1  2     0
1  3     0
1  4     1
2  1     1
2  2     0
2  3     3
2  4     1
省略100行
我想使用for循环获得如下数据帧:

new_df <- months_since_last_purchase(df)
id月购买最近期
1 13 NA
1  2     0          1
1  3     0          2
1  4     1          3
2 1不适用
2  2     0          1
2  3     3          2
2  4     1          1
省略100行

获取
购买的
最新信息0是最难的部分。使用dplyr的一种方法是

library(dplyr)

df %>%
  group_by(id, group = cumsum(purchases != 0)) %>%
  mutate(recency = month - first(month)) %>%
  ungroup() %>%
  select(-group) %>%
  group_by(id) %>%
  mutate(recency = ifelse(recency == 0, lag(recency) + month - lag(month), recency))

#     id month purchases recency
#  <int> <int>     <int>   <int>
#1     1     1         3      NA
#2     1     2         0       1
#3     1     3         0       2
#4     1     4         1       3
#5     2     1         1      NA
#6     2     2         0       1
#7     2     3         3       2
#8     2     4         1       1

这几乎就是我们想要的,除了相同的
id
where
购买!=0
我们需要用最近的非0值减去它,我们使用另一个
group\u by
id
ifelse
来获得这个值,我知道你想要一个for循环的答案。这里有一个:

months_since_last_purchase <- function(df) {

  df$recency <- NA           # create an empty vector to store recency
  months_since = 0           # initialise our months since counter to zero

  for(row in 1:nrow(df)){    # loop through our rows

    if(df$purchases[row] == 0){  # if we did not purchase something this month

      months_since = months_since + 1   # increment months_since
      df$recency[row] <- months_since   # set the recency to months since

    } else {                     # else if we did purchase something this month

      months_since = months_since + 1   # increment months_since
      if(months_since == 1){   #     and if we purchased something last month as well
        df$recency[row] = NA   #         set the recency to NA
      }else{                   #     else we didn't purchase something last month
        df$recency[row] <- months_since    # set the recency to the months_since
      }
      months_since = 0         # reset the months since to zero

    }
  }
  df                           # return the modified dataframe
}
输出:

     id month purchases recency
1     1     1         3      NA
2     1     2         0       1
3     1     3         0       2
4     1     4         1       3
5     2     1         1      NA
6     2     2         0       1
7     2     3         3       2
8     2     4         1      NA

R经常不赞成for循环,因为向量运算更快、更优雅,但当速度不重要时,我仍然觉得for循环很方便。

我把代码放在RStudio中,它说“有50个或更多的警告(使用warnings()查看前50个)”@ZoeyYing ok。这些是警告,而不是错误。你能用上述方法检查输出吗?它能给你你想要的吗?@ZoeyYing你的数据框中可能有
NA
s。您能确认哪列有
NA
s和吗。你想用它们做什么?我试着在我的RStudio中运行这段代码,但是新df的输出只显示旧的数据帧。抱歉,也许我应该更明确一些。我的代码创建了一个名为
months\u\u since\u purchase()
的函数,只需复制、粘贴并点击enter键即可使用该函数创建函数,然后使用它来隐藏您的df用法:
new\u df
     id month purchases recency
1     1     1         3      NA
2     1     2         0       1
3     1     3         0       2
4     1     4         1       3
5     2     1         1      NA
6     2     2         0       1
7     2     3         3       2
8     2     4         1      NA