我有一个类似于下面的数据框,除了我有17个变量(如Var1
和Var2
)而不是2。
df <- read.table(header = TRUE, text =
"STUD_ID Var1 Var2
1 0 0
1 0 1
2 1 2
3 3 0", stringsAsFactors = FALSE)
我想创建一个新列,输出&#34;是&#34;如果17个变量中的任何一个具有值1,2或3,并且&#34; No&#34;除此以外。我想要的输出是:
# STUD_ID Var1 Var2 Output
# 1 0 0 "No"
# 1 0 1 "Yes"
# 2 1 2 "Yes"
# 3 3 0 "Yes"
我尝试了以下代码,但它给出了错误,我不想复制粘贴部分代码17次:
df %>%
mutate(output = if_else(var1 %in% 1:3 |
var2 %in% 1:3, 1, 0))
答案 0 :(得分:2)
尝试尽可能向量化(但仍然没有转换为字符串的效率)的一种方法是使用do.call
粘贴行和grepl
所需的值,即
ifelse(grepl('1|2|3', do.call(paste0, df[-1])), 'Yes', 'No')
#[1] "No" "Yes" "Yes" "Yes"
答案 1 :(得分:2)
我们可以使用base R
df$Output <- c("No", "Yes")[Reduce(`|`, lapply(df[-1], `%in%`, 1:3)) + 1]
df$Output
#[1] "No" "Yes" "Yes" "Yes"
或tidyverse
library(tidyverse)
df %>%
mutate_at(vars(matches("Var")), funs(. %in% 1:3)) %>%
select(-STUD_ID) %>%
reduce( `|`) %>% {c('No', 'Yes')[. + 1]} %>%
mutate(df, output = .)
# STUD_ID Var1 Var2 output
#1 1 0 0 No
#2 1 0 1 Yes
#3 2 1 2 Yes
#4 3 3 0 Yes
答案 2 :(得分:1)
一个选项如下:
df$Output = sapply(seq(1,nrow(df)),
function(x) {ifelse(any(df[x,c(2:3)] %in% c(1,2,3)),"Yes","No")})
您可以使用列索引的范围或具有列名称的数组替换c(2:3)
。希望这会有所帮助。
答案 3 :(得分:1)
你可以添加所有17个变量,如果sum大于0,那么它意味着至少有一个非零值
> df$VarNew=df$Var1+df$Var2
> df
STUD_ID Var1 Var2 VarNew
1 1 0 0 0
2 1 0 1 1
3 2 1 2 3
4 3 3 0 3
> df$VarNew2=ifelse(df$VarNew>0,"Yes","No")
> df
STUD_ID Var1 Var2 VarNew VarNew2
1 1 0 0 0 No
2 1 0 1 1 Yes
3 2 1 2 3 Yes
4 3 3 0 3 Yes