R 按客户id计算购买日期的平均差异
我想知道如何使用R来计算下面的值R 按客户id计算购买日期的平均差异,r,R,我想知道如何使用R来计算下面的值 假设CSV包含以下购买数据: | Customer ID | Purchase Date | | 1 | 01/01/2017 | | 2 | 01/01/2017 | | 3 | 01/01/2017 | | 4 | 01/01/2017 | | 1 | 02/01/2017 | | 2 | 03
| Customer ID | Purchase Date |
| 1 | 01/01/2017 |
| 2 | 01/01/2017 |
| 3 | 01/01/2017 |
| 4 | 01/01/2017 |
| 1 | 02/01/2017 |
| 2 | 03/01/2017 |
| 2 | 07/01/2017 |
| Customer ID | AVG repurchase |
| 1 | 30 days | = (02/01 - 01/01 / 1 order
| 2 | 90 days | = ( (03/01 - 01/01) + (07 - 3/1) ) /2 orders
| 3 | n/a |
| 4 | n/a |
我假设您已将CSV读入名为
df
的数据框中,并且我已使用重命名变量,因为名称中有空格的变量,这导致许多变量使用snake case或变量命名约定
下面是一个基本的R解决方案:
mean(sapply(by(df$purchase_date, df$customer_id, diff), mean), na.rm=TRUE)
[1] 60.75
您可能会注意到,我们得到的是60.75
,而不是您预期的60。这是因为客户1的购买间隔为31天(1月至2月1日为31天),而客户2的购买间隔也类似——一个月内并不总是30天
解释
by()
函数通过分组将另一个函数应用于数据。这里,我们通过df$customer\u id
的唯一值将diff()
应用于df$purchase\u date
。这本身将产生以下输出:
df$customer_id: 1
Time difference of 31 days
-----------------------------------------------------------
df$customer_id: 2
Time differences in days
[1] 59 122
然后我们使用
sapply(by(df$purchase_date, df$customer_id, diff), mean)
将mean()
应用于上一个结果的元素。这为我们提供了每位客户的平均回购时间:
1 2 3 4
31.0 90.5 NaN NaN
(我们看到客户3和客户4从未回购)。最后,我们需要平均这些平均回购时间,这意味着我们还需要处理那些NaN
值,因此我们使用:
mean(sapply(by(df$purchase_date, df$customer_id, diff), mean), na.rm=TRUE)
这将平均以前的结果,忽略缺失的值(在R中)。这里是另一个使用
dplyr
+lubridate
的解决方案:
library(dplyr)
library(lubridate)
df %>%
mutate(Purchase_Date = mdy(Purchase_Date)) %>%
group_by(Customer_ID) %>%
summarize(AVG_Repurchase = sum(difftime(Purchase_Date,
lag(Purchase_Date), units = "days"),
na.rm=TRUE)/(n()-1))
或使用数据。表:
library(data.table)
setDT(df)[, Purchase_Date := mdy(Purchase_Date)]
df[, .(AVG_Repurchase = sum(difftime(Purchase_Date,
shift(Purchase_Date), units = "days"),
na.rm=TRUE)/(.N-1)), by = "Customer_ID"]
结果:
# A tibble: 4 x 2
Customer_ID AVG_Repurchase
<dbl> <time>
1 1 31.0 days
2 2 90.5 days
3 3 NaN days
4 4 NaN days
Customer_ID AVG_Repurchase
1: 1 31.0 days
2: 2 90.5 days
3: 3 NaN days
4: 4 NaN days
df = structure(list(Customer_ID = c(1, 2, 3, 4, 1, 2, 2), Purchase_Date = c(" 01/01/2017",
" 01/01/2017", " 01/01/2017", " 01/01/2017", " 02/01/2017", " 03/01/2017",
" 07/01/2017")), .Names = c("Customer_ID", "Purchase_Date"), class = "data.frame", row.names = c(NA,
-7L))
你能给我们提供你的数据帧的代码吗?您可以使用dput()
函数获得它。这太棒了,谢谢。出于某种原因,我在by(…)函数调用中收到一个错误:`` as.character.factor(x)中的错误:格式错误的因子```代码:``基本上是`` as.character.factor(x):格式错误的因子``中的错误。试图更新我的评论,但格式错误。。。haI认为,只有通过拥有您的数据,才能重现此错误,并因此修复/解决此错误。如果将dput(orders)
的输出添加到问题中,可能会有所帮助。作为将来的参考,如果你一开始就这样做,你通常会得到更好的答案(这就是为什么芭芭拉会留下这样的评论)。谢谢。对不起,我对R还是新手-我从这个帖子中学到了很多。通过将DF中的字段转换为日期字段,我使它一切正常。df$购买日期
df = structure(list(Customer_ID = c(1, 2, 3, 4, 1, 2, 2), Purchase_Date = c(" 01/01/2017",
" 01/01/2017", " 01/01/2017", " 01/01/2017", " 02/01/2017", " 03/01/2017",
" 07/01/2017")), .Names = c("Customer_ID", "Purchase_Date"), class = "data.frame", row.names = c(NA,
-7L))