我想使用dplyr逐行遍历数据帧,如果A == 0,则设置B为B上一行的值,否则保持不变.但是,我希望" B在前一行中的值"在计算过程中引用前一行,而不是在计算开始之前,因为值可能已经改变 - 换句话说,我希望更改向下传播.例如,使用以下数据:
dat <- data.frame(A=c(1,0,0,0,1),B=c(0,1,1,1,1))
A B
1 0
0 1
0 1
0 1
1 1
Run Code Online (Sandbox Code Playgroud)
我想计算的结果是:
result <- data.frame(A=c(1,0,0,0,1),B=c(0,0,0,0,1))
A B
1 0
0 0
0 0
0 0
1 1
Run Code Online (Sandbox Code Playgroud)
如果我使用类似的东西,result <- dat %>% mutate(B = ifelse(A==0,lag(B),B)则更改不会向下传播:结果$ B将等于c(0,0,1,1,1),而不是c(0,0,0,0,1).
更一般地说,如何使用dplyr :: mutate创建依赖于自身的列(因为它在计算过程中更新,而不是之前的更新)?
好像你想要一个"最后观察结转"的方法.最常见的R实现是用最后一个观察值zoo::na.locf填充NA值.在这种情况下我们需要做的就是首先设置NA我们要填写的所有B值:
mutate(dat,
B = ifelse(A == 0, NA, B),
B = zoo::na.locf(B))
# A B
# 1 1 0
# 2 0 0
# 3 0 0
# 4 0 0
# 5 1 1
Run Code Online (Sandbox Code Playgroud)
至于我的评论,请注意,唯一的办法mutate是将列添加到数据框中.我们也可以在没有变异的情况下做到这一点:
result = dat
result$B = with(result, ifelse(A == 0, NA, B))
result$B = zoo::na.locf(result$B)
Run Code Online (Sandbox Code Playgroud)
无论您使用mutate或者[或使用$任何其他方法来访问/添加列都与问题相关.