在以下数据框中,我想创建一个名为D2的新列,该列与相应的A,B或C列匹配。例如,如果D == A,我想要D2 == A2。
A A2 B B2 C C2 D
1 10 2 90 3 9 1
1 11 2 99 3 15 1
1 42 2 2 3 9 2
1 5 2 54 3 235 2
1 13 2 20 3 10 3
1 6 2 1 3 4 3
这就是我希望新数据框看起来像:
A A2 B B2 C C2 D D2
1 10 2 90 3 9 1 10
1 11 2 99 3 15 1 11
1 42 2 2 3 9 2 2
1 5 2 54 3 235 2 54
1 13 2 20 3 10 3 10
1 6 2 1 3 4 3 4
我使用dplyr使用ifelse语句成功完成了这项操作,但由于我使用了很多列来执行此操作,因此在一段时间后会变得乏味。我想知道是否有更聪明的方法来完成同样的任务。
library(dplyr)
newdata <- olddata %>% mutate(D2=ifelse(D==A,A2,ifelse(D==B,B2,C2)))
答案 0 :(得分:1)
我们可以使用max.col
中的base R
高效执行此操作。将'olddata'子集仅设置为'A','B','C'列('d1'),检查它是否等于'D'(复制'D'以匹配长度)后,使用{{ 1}}找到最大元素的索引(即在这种情况下为TRUE,假设每行将有一个TRUE值),乘以2,因为'A1','B2','C2'列是交替的在'A','B','C',max.col
之后用行序列创建行/列索引并根据该元素提取元素以创建'D2'列。
cbind
稍微不同的方法是使用d1 <- olddata[c("A", "B", "C")]
olddata$D2 <- olddata[cbind(1:nrow(d1), max.col(d1 == rep(olddata["D"],
ncol(d1)), "first")*2)]
olddata$D2
#[1] 10 11 2 54 10 4
在循环中单独比较列(如果数据集非常大则应该有效,因为转换为大逻辑lapply
会花费内存)和基于此,我们使用matrix
mapply