R 检查向量中与变量名对应的元素是否属于数据帧中的字符类
我正试图为我的功能建立一个安全锁销。 我希望它获取一个数据帧的输入和一个变量名向量来检查类。我想让它尝试强制任何无法指定字符的变量,发送警告,或者如果强制失败,停止进程 到目前为止,我得到的是:R 检查向量中与变量名对应的元素是否属于数据帧中的字符类,r,function,dataframe,dplyr,purrr,R,Function,Dataframe,Dplyr,Purrr,我正试图为我的功能建立一个安全锁销。 我希望它获取一个数据帧的输入和一个变量名向量来检查类。我想让它尝试强制任何无法指定字符的变量,发送警告,或者如果强制失败,停止进程 到目前为止,我得到的是: #Inputs varlist <- c("varA","varB","varC") df <- data.frame(matrix(ncol=4,nrow=0, dimnames=list(NULL, c("varA", "varB", "varC","varD")))) df$varA
#Inputs
varlist <- c("varA","varB","varC")
df <- data.frame(matrix(ncol=4,nrow=0, dimnames=list(NULL, c("varA", "varB", "varC","varD"))))
df$varA <- as.character(df$varA)
df$varB <- as.character(df$varB)
df$varC <- as.factor(df$varC)
df$varD <- as.numeric(df$varD)
for(i in 1:length(varlist)){
if(!(purrr::pmap(select(df, varlist[i]), ~is.character)==TRUE)){
df$varlist[i] <- as.character(df$varlist[i])
warning(paste0("Coercing variable", varlist[i], "to character"))
stopifnot(is.character(df$varlist[i]))
}
}
有没有一个简单的方法可以做到这一点
预期产出
#output console warning
Warning: Coercing variable varC to character
#Manual checks
is.character(df$varA) == TRUE #included in varlist
is.character(df$varB) == TRUE #included in varlist
is.character(df$varC) == TRUE #included in varlist, coerced from factor to character
is.character(df$varD) == FALSE #not included in varlist
我有一些我认为可以在for循环中工作的东西。如果您的数据帧相当大并且有很多列,那么有一种方法可以应用它来加速它,但是这与您最初拥有的数据帧更接近 制作数据
varlist <- c("varA","varB","varC")
df <- data.frame(varA = letters[1:4],
varB = letters[11:14],
varC = letters[21:24],
varD = 1:4)
df$varA <- as.character(df$varA)
df$varB <- as.character(df$varB)
df$varC <- as.factor(df$varC)
df$varD <- as.numeric(df$varD)
使用Map
更新以使用Map
执行相同的操作,这是apply的多变量版本:
char_function <- function(x, name){
y <- as.character(x)
if(!(is.character(x))){
warning((paste("Coercing variable", name, "to character")))
}
return(y)
}
df.char <- data.frame(Map(char_function, df[varlist], names(df[varlist])), stringsAsFactors = F)
char\u函数您的示例显示0行的df
。。你的期望是什么output@akrun更新问题,包括控制台警告和肯定检查。映射通常用于并行迭代。您这样做是因为您正在迭代列和列名,但实际上并不需要这样做。(另外,as.character
足够聪明,不会对已经是character
的东西做任何事情——你不需要为此创建包装器。)你可以直接使用lappy
和df.char=data.frame(lappy(df,as.character),stringsafactors=F)
,或者如果就地修改df[]=lappy(df,char_函数)
。这与OP的varlist
,df[varlist]=lappy(df[varlist],as.characteracter)配合得很好
哦,我完全没有意识到OP只想检查varlist
中的某些变量。我包装了函数,以便它返回OP想要的警告。不知道如何在不编写明确包含它的函数的情况下执行此操作。但我将编辑响应以包含您的注释
for(i in (1:ncol(df))[colnames(df) %in% varlist]){
df[,i] <- as.character(df[,i])
if(!(is.character(df[,i]))){
warning(paste("Coercing variable", colnames(df)[i], "to character"))
}
}
char_function <- function(x, name){
y <- as.character(x)
if(!(is.character(x))){
warning((paste("Coercing variable", name, "to character")))
}
return(y)
}
df.char <- data.frame(Map(char_function, df[varlist], names(df[varlist])), stringsAsFactors = F)