如何在 R 中根据帐户和时间间隔(例如最后一天、上周、上个月等)创建新功能?
How to create new features based on accounts and time intervals such as last day, last week, last month, etc in R?
PS:我的数据有一百万行,所以我正在寻找一种不会花很长时间 运行 大数据的解决方案。
这是我的交易数据
id from to date amount
<int> <fctr> <fctr> <date> <dbl>
19521 6644 6934 2005-01-01 700.0
19524 6753 8456 2005-01-01 600.0
19523 9242 9333 2005-01-01 1000.0
19522 9843 9115 2005-01-01 900.0
19525 7075 6510 2005-02-01 400.0
19526 8685 7207 2005-02-01 1100.0
… … … … …
1052337 9866 5992 2010-12-31 139.1
1052768 9866 5797 2010-12-31 72.1
1054271 9866 6697 2010-12-31 95.8
1055597 9866 9736 2010-12-31 278.9
1053519 9868 8644 2010-12-31 242.8
1052790 9869 8399 2010-12-31 372.2
我想根据“来自”列中的帐户和时间间隔(例如最后一天、上周、上个月等)创建新功能
例如,我想计算上 day/last week/last 个月发送的“发件人”列中帐户的最大金额,并将此信息作为新列保存到数据中
以下数据是我期望的输出:
id from to date amount max_amount_in_last_day max_amount_in_last_week max_amount_in_last_month max_amount_in_last_3month
<int> <fctr> <fctr> <date> <dbl> <dbl> <dbl> <dbl> <dbl>
19521 6644 6934 2005-01-01 700.0 700.0 700.0 700.0 700.0
16214 6644 6874 2005-06-30 288.8 288.8 288.8 288.8 288.8
16806 6644 9746 2005-06-30 83.7 288.8 288.8 288.8 288.8
15220 6644 6671 2005-07-23 21716.0 21716.0 21716.0 21716.0 21716.0
11975 6644 5384 2005-08-31 216.7 216.7 216.7 216.7 21716.0
26579 6644 6041 2005-12-31 159.2 159.2 159.2 159.2 159.2
35893 6644 8567 2006-01-31 169.6 169.6 169.6 169.6 169.6
39425 6644 5599 2006-02-12 16230.0 16230.0 16230.0 16230.0 16230.0
43606 6644 6454 2006-03-06 5859.0 5859.0 5859.0 16230.0 16230.0
52052 6644 8836 2006-04-13 7269.0 7269.0 7269.0 7269.0 16230.0
...
我怎样才能做到这一点?
为了计算max_amount_in_last_day
,我尝试了以下代码,但它在大型数据集上的效果很差。有更好的方法吗?
y <- NULL
for(i in data$id){
date <- data[data$id==i,]$date
acc <- data[data$id==i,]$from
df <- data[data$from==acc & data$date==date,]
df <- df %>% mutate(max_trx_amount_in_last_day=max(df$amount))
tmp <- df
y <- rbind(y, tmp) %>% distinct
}
y
首先,定义一个函数来计算您想要的前几天的统计数据。
previousDays <- function(X, from, date, days, FUN){
FUN <- match.fun(FUN)
Y <- X[X[['from']] == from, ]
i <- Y[['date']] >= date - days + 1 & Y[['date']] <= date
if(sum(i) > 0) FUN(Y[i, 'amount']) else NA_real_
}
现在,按指定的天数将函数应用于每一行。在下面的例子中,7
天,上周。
applyPrev <- function(X, days, FUN){
FUN <- match.fun(FUN)
sapply(seq_along(X[['id']]), function(i){
f <- X[i, 'from']
d <- X[i, 'date']
previousDays(df1, f, d, days, FUN)
})
}
applyPrev(df1, 7, max)
数据
df1 <- read.table(text = "
id from to date amount
19521 6644 6934 2005-01-01 700.0
19524 6753 8456 2005-01-01 600.0
19523 9242 9333 2005-01-01 1000.0
19522 9843 9115 2005-01-01 900.0
19525 7075 6510 2005-02-01 400.0
19526 8685 7207 2005-02-01 1100.0
1052337 9866 5992 2010-12-31 139.1
1052768 9866 5797 2010-12-31 72.1
1054271 9866 6697 2010-12-31 95.8
1055597 9866 9736 2010-12-31 278.9
1053519 9868 8644 2010-12-31 242.8
1052790 9869 8399 2010-12-31 372.2
", header = TRUE)
PS:我的数据有一百万行,所以我正在寻找一种不会花很长时间 运行 大数据的解决方案。
这是我的交易数据
id from to date amount
<int> <fctr> <fctr> <date> <dbl>
19521 6644 6934 2005-01-01 700.0
19524 6753 8456 2005-01-01 600.0
19523 9242 9333 2005-01-01 1000.0
19522 9843 9115 2005-01-01 900.0
19525 7075 6510 2005-02-01 400.0
19526 8685 7207 2005-02-01 1100.0
… … … … …
1052337 9866 5992 2010-12-31 139.1
1052768 9866 5797 2010-12-31 72.1
1054271 9866 6697 2010-12-31 95.8
1055597 9866 9736 2010-12-31 278.9
1053519 9868 8644 2010-12-31 242.8
1052790 9869 8399 2010-12-31 372.2
我想根据“来自”列中的帐户和时间间隔(例如最后一天、上周、上个月等)创建新功能
例如,我想计算上 day/last week/last 个月发送的“发件人”列中帐户的最大金额,并将此信息作为新列保存到数据中
以下数据是我期望的输出:
id from to date amount max_amount_in_last_day max_amount_in_last_week max_amount_in_last_month max_amount_in_last_3month
<int> <fctr> <fctr> <date> <dbl> <dbl> <dbl> <dbl> <dbl>
19521 6644 6934 2005-01-01 700.0 700.0 700.0 700.0 700.0
16214 6644 6874 2005-06-30 288.8 288.8 288.8 288.8 288.8
16806 6644 9746 2005-06-30 83.7 288.8 288.8 288.8 288.8
15220 6644 6671 2005-07-23 21716.0 21716.0 21716.0 21716.0 21716.0
11975 6644 5384 2005-08-31 216.7 216.7 216.7 216.7 21716.0
26579 6644 6041 2005-12-31 159.2 159.2 159.2 159.2 159.2
35893 6644 8567 2006-01-31 169.6 169.6 169.6 169.6 169.6
39425 6644 5599 2006-02-12 16230.0 16230.0 16230.0 16230.0 16230.0
43606 6644 6454 2006-03-06 5859.0 5859.0 5859.0 16230.0 16230.0
52052 6644 8836 2006-04-13 7269.0 7269.0 7269.0 7269.0 16230.0
...
我怎样才能做到这一点?
为了计算max_amount_in_last_day
,我尝试了以下代码,但它在大型数据集上的效果很差。有更好的方法吗?
y <- NULL
for(i in data$id){
date <- data[data$id==i,]$date
acc <- data[data$id==i,]$from
df <- data[data$from==acc & data$date==date,]
df <- df %>% mutate(max_trx_amount_in_last_day=max(df$amount))
tmp <- df
y <- rbind(y, tmp) %>% distinct
}
y
首先,定义一个函数来计算您想要的前几天的统计数据。
previousDays <- function(X, from, date, days, FUN){
FUN <- match.fun(FUN)
Y <- X[X[['from']] == from, ]
i <- Y[['date']] >= date - days + 1 & Y[['date']] <= date
if(sum(i) > 0) FUN(Y[i, 'amount']) else NA_real_
}
现在,按指定的天数将函数应用于每一行。在下面的例子中,7
天,上周。
applyPrev <- function(X, days, FUN){
FUN <- match.fun(FUN)
sapply(seq_along(X[['id']]), function(i){
f <- X[i, 'from']
d <- X[i, 'date']
previousDays(df1, f, d, days, FUN)
})
}
applyPrev(df1, 7, max)
数据
df1 <- read.table(text = "
id from to date amount
19521 6644 6934 2005-01-01 700.0
19524 6753 8456 2005-01-01 600.0
19523 9242 9333 2005-01-01 1000.0
19522 9843 9115 2005-01-01 900.0
19525 7075 6510 2005-02-01 400.0
19526 8685 7207 2005-02-01 1100.0
1052337 9866 5992 2010-12-31 139.1
1052768 9866 5797 2010-12-31 72.1
1054271 9866 6697 2010-12-31 95.8
1055597 9866 9736 2010-12-31 278.9
1053519 9868 8644 2010-12-31 242.8
1052790 9869 8399 2010-12-31 372.2
", header = TRUE)