我想将vales分配给命名向量,具体取决于我通过行循环的df中的值。我根据文档看到案例的RHS是一个向量,而我试图做的是让RHS成为一个实际的分配步骤。这可能吗? Case_when在这里比使用if语句更优雅:
test.df <- data.frame(cat1 = c('label1', 'label2', 'label3'),
cat2 = c('label3', '', ''),
cat3 = c('', 'label2', 'label1'))
test.lst <- apply(test.df, 1, function(x){
test.vec <- c(label1 = 0, label2 = 0, label3 = 0)
case_when(
x[['cat1']]=='label1' | x[['cat2']]=='label1' | x[['cat3']]=='label1' ~ test.vec['label1'] <- 1,
x[['cat1']]=='label2' | x[['cat2']]=='label2' | x[['cat3']]=='label2' ~ test.vec['label2'] <- 1,
x[['cat1']]=='label3' | x[['cat2']]=='label3' | x[['cat3']]=='label3' ~ test.vec['label3'] <- 1
)
})
答案 0 :(得分:4)
您可以使用local:CustomizableTreeBaseItem
包中的transmute
函数仅保留在函数调用中创建/修改的列。因此,您可以创建一个全新的数据帧。它看起来像这样:
dplyr
,您的输出将如下所示:
test.lst <- test.df %>%
transmute(label1 = case_when(
cat1 == "label1" | cat2 == "label1" | cat3 == "label1" ~ 1,
TRUE ~ 0
),
label2 = case_when(
cat1 == "label2" | cat2 == "label2" | cat3 == "label2" ~ 1,
TRUE ~ 0
),
labels3 = case_when(
cat1 == "label3" | cat2 == "label3" | cat3 == "label3" ~ 1,
TRUE ~ 0
))
注意, label1 label2 labels3
1 1 0 1
2 0 1 0
3 1 0 1
包及其大部分功能都是矢量化的。因此,他们已经对每一行执行了所需的操作,而无需dplyr
循环或for
/ apply
函数。这样可以加快代码速度并使其更具可读性。
答案 1 :(得分:0)
case_when
不是必需的,这是另一种解决方案:
sapply(paste0('label', 1:3), function(x) sign(rowSums(as.matrix(test.df) == x)) )
# label1 label2 label3
# [1,] 1 0 1
# [2,] 0 1 0
# [3,] 1 0 1