如何最好地将具有 NA 的两个因素合并为一个变量
How best to collapse two factors with NAs into one variable
我有很多这样的变量集:
Var1 Var2
"Asian" NA
NA "Black"
"White" NA
我想方便地把它们写成这种形式:
Race
"Asian"
"Black"
"White"
我一直在尝试类似的方法:
Race <- ifelse(is.na(Var1), Var2, Var1)
但这会将值转换为级别的数字,并且数字不匹配(例如,产生 1, 1, 2
)。有没有一种方便的方法来做到这一点(最好使用简短的、不言自明的代码)? (你可以用 as.character
摆脱这个,但必须有更好的方法。)
这个解决方案怎么样?:
ind <- apply(df, 1, function(x) which(!is.na(x)))
df[cbind(seq_along(ind), ind)]
[1] "Asian" "Black" "White"
通过 as.character
进行中间转换:
假设这是您的数据:
dat <- data.frame(Var1=c("Asian",NA,"White"),Var2=c(NA,"Black",NA))
do.call(pmax,c(lapply(dat,as.character),na.rm=TRUE))
#[1] "Asian" "Black" "White"
如果您需要处理特定的子集,您可以这样做:
do.call(pmax,c(lapply(dat[c("Var1","Var2")],as.character),na.rm=TRUE))
不需要 as.character
的替代方案是:
dat[cbind(1:nrow(dat),max.col(!is.na(dat)))]
#[1] "Asian" "Black" "White"
另一个解决方案(我同意这很奇怪而且很短,您的列需要像您的示例中那样具有特征):
> library(tidyr)
> unite(replace(df, is.na(df), ""), V, c(Var1, Var2), sep=''))$V
#[1] "Asian" "Black" "White"
或者,使用 gsub 可能有风险,但这里 NA 是字符链的一部分,所以很安全:
> gsub("NA", "", unite(df, V, c(Var1, Var2), sep='')$V)
#[1] "Asian" "Black" "White"
我有很多这样的变量集:
Var1 Var2
"Asian" NA
NA "Black"
"White" NA
我想方便地把它们写成这种形式:
Race
"Asian"
"Black"
"White"
我一直在尝试类似的方法:
Race <- ifelse(is.na(Var1), Var2, Var1)
但这会将值转换为级别的数字,并且数字不匹配(例如,产生 1, 1, 2
)。有没有一种方便的方法来做到这一点(最好使用简短的、不言自明的代码)? (你可以用 as.character
摆脱这个,但必须有更好的方法。)
这个解决方案怎么样?:
ind <- apply(df, 1, function(x) which(!is.na(x)))
df[cbind(seq_along(ind), ind)]
[1] "Asian" "Black" "White"
通过 as.character
进行中间转换:
假设这是您的数据:
dat <- data.frame(Var1=c("Asian",NA,"White"),Var2=c(NA,"Black",NA))
do.call(pmax,c(lapply(dat,as.character),na.rm=TRUE))
#[1] "Asian" "Black" "White"
如果您需要处理特定的子集,您可以这样做:
do.call(pmax,c(lapply(dat[c("Var1","Var2")],as.character),na.rm=TRUE))
不需要 as.character
的替代方案是:
dat[cbind(1:nrow(dat),max.col(!is.na(dat)))]
#[1] "Asian" "Black" "White"
另一个解决方案(我同意这很奇怪而且很短,您的列需要像您的示例中那样具有特征):
> library(tidyr)
> unite(replace(df, is.na(df), ""), V, c(Var1, Var2), sep=''))$V
#[1] "Asian" "Black" "White"
或者,使用 gsub 可能有风险,但这里 NA 是字符链的一部分,所以很安全:
> gsub("NA", "", unite(df, V, c(Var1, Var2), sep='')$V)
#[1] "Asian" "Black" "White"