R:如果两个值中的至少一个为零,则找到差异

时间:2017-06-01 15:08:08

标签: r diff

如果至少有一个值为零,我想计算行的abs(差异)(当前行的当前行)。如果两个值都是非零值,则应返回0.

示例:列'A'显示初始数据,'Diff'显示我想要的内容:

df <- data.frame(A=c(0,0,1,2,3,4,0,0),Diff=c(0,0,1,0,0,0,4,0))

由于

2 个答案:

答案 0 :(得分:0)

以下是使用 dplyr 包和lag函数的方法:

library(dplyr)
df1 <- data.frame(A=c(0,0,1,2,3,4,0,0),Diff=c(0,0,1,0,0,0,4,0))
df1 %>%
    mutate(lag_A = lag(A),
           Diff2 = abs(A - lag_A)) %>%
    mutate(Diff2 = ifelse(is.na(lag_A), 0,
                  ifelse(A == 0 | lag_A == 0, Diff2, 0)))

  A Diff lag_A Diff2
1 0    0    NA     0
2 0    0     0     0
3 1    1     0     1
4 2    0     1     0
5 3    0     2     0
6 4    0     3     0
7 0    4     4     4
8 0    0     0     0

然后,您可以使用select函数来获取所需的列。我离开了表格中的所有列来说明解决方案。

答案 1 :(得分:0)

假设

我会假设Diff的第一个值不是你想要的操作的结果,因为A的第一个值没有前面的值,所以我选择在答案上重复它,但您可以添加任何内容而不是A[1]

编辑:我还假设你想要一个仅使用base的解决方案,否则,bouncyball的解决方案就像魅力一样。

解决方案

Diff = rep(0,(length(A)-1))
Diff[which(mapply(xor,A[-1],A[-length(A)]))] = abs(A[-1][which(mapply(xor,A[-1],A[-length(A)]))]-A[-length(A)][which(mapply(xor,A[-1],A[-length(A)]))])
Diff = c(A[1],Diff)

你可以通过使它成为这样的命名函数来改进:

foo = function(A){
    Diff = rep(0,(length(A)-1))
    Diff[which(mapply(xor,A[-1],A[-length(A)]))] = abs(A[-1][which(mapply(xor,A[-1],A[-length(A)]))]-A[-length(A)][which(mapply(xor,A[-1],A[-length(A)]))])
    Diff = c(A[1],Diff)
    Diff
}

说明

我们使用以下代码而不是操作A: A[-1],产生0 1 2 3 4 0 0(等于A但没有第一个元素) 和A[-length(A)],产生:0 0 1 2 3 4 0(等于A,但没有最后一个元素)。

如果我们从后者中减去第一个,我们将元素减法正确,但我们仍然需要知道 这些减法需要发生。

通过组合函数xormapplywhich(所有这些都是基础成员),如下所示:

which(mapply(xor,A[-1],A[-length(A)]))我们发现:

2 6这是A [-1]和A [-length(A)]中的位置的索引,其中应该进行减法。

现在我们使用:

创建一个名为Diff的0向量与我们的新向量大小相同

Diff = rep(0,length(A)-1),然后我们使用:

仅更改不应包含0的索引

Diff[which(mapply(xor,A[-1],A[-length(A)]))] = abs(A[-1][which(mapply(xor,A[-1],A[-length(A)]))]-A[-length(A)][which(mapply(xor,A[-1],A[-length(A)]))])

最后我们使用Diff = c(A[1],Diff)再次放回第一个元素。