Quel est le moyen le plus efficace de convertir plusieurs colonnes dans un cadre de données du format de caractères au format numérique?
J'ai un dataframe appelé DF avec toutes les variables de caractère.
Je voudrais faire quelque chose comme
for (i in names(DF){
DF$i <- as.numeric(DF$i)
}
Je vous remercie
Tu pourrais essayer
DF <- data.frame("a" = as.character(0:5),
"b" = paste(0:5, ".1", sep = ""),
"c" = letters[1:6],
stringsAsFactors = FALSE)
# Check columns classes
sapply(DF, class)
# a b c
# "character" "character" "character"
cols.num <- c("a","b")
DF[cols.num] <- sapply(DF[cols.num],as.numeric)
sapply(DF, class)
# a b c
# "numeric" "numeric" "character"
Vous pouvez utiliser l'index des colonnes: data_set[,1:9] <- sapply(dataset[,1:9],as.character)
Si vous utilisez déjà le Tidyverse, il existe plusieurs solutions en fonction de la situation:
library(dplyr)
library(magrittr)
# solution
dataset %<>% mutate_if(is.character,as.numeric)
# to test
df <- data.frame(
x1 = c('1','2','3'),
x2 = c('4','5','6'),
x3 = c('1','a','b'), # vector with alpha characters
stringsAsFactors = F)
# display starting structure
df %>% str()
Convertir tous les vecteurs de caractères en numériques (ils pourraient échouer s'ils n'étaient pas numériques)
df %>%
select(-x3) %>% # this removes the alpha column if all your character columns need converted to numeric
mutate_if(is.character,as.numeric) %>%
str()
Vérifiez si chaque colonne peut être convertie. Cela peut être une fonction anonyme. Il vérifie si as.numeric renvoie NA. Il vérifie également si c'est un vecteur de caractère pour ignorer les facteurs. Cela supprime également les avertissements puisque vous savez que les AN seront introduites volontairement et vérifiées ultérieurement.
numericcharacters <- function(x) {
!any(is.na(suppressWarnings(as.numeric(x)))) & is.character(x)
}
df %>%
mutate_if(numericcharacters,as.numeric) %>%
str()
Si vous voulez convertir des colonnes nommées spécifiques, alors mutate_at est préférable.
df %>% mutate_at('x1',as.numeric) %>% str()
Je pense que je l'ai compris. Voici ce que j’ai fait (la solution n’est peut-être pas la plus élégante - des suggestions sur la manière de l’améliorer sont les bienvenues)
#names of columns in data frame
cols <- names(DF)
# character variables
cols.char <- c("fx_code","date")
#numeric variables
cols.num <- cols[!cols %in% cols.char]
DF.char <- DF[cols.char]
DF.num <- as.data.frame(lapply(DF[cols.num],as.numeric))
DF2 <- cbind(DF.char, DF.num)
Je me rends compte que c’est un vieux sujet mais je voulais poster une solution similaire à votre demande de fonction (je viens de rencontrer le problème similaire moi-même en essayant de formater un tableau entier en libellés de pourcentage).
Supposons que vous ayez un df avec 5 colonnes de caractères à convertir. Tout d'abord, je crée un tableau contenant les noms des colonnes que je veux manipuler:
col_to_convert <- data.frame(nrow = 1:5
,col = c("col1","col2","col3","col4","col5"))
for (i in 1:max(cal_to_convert$row))
{
colname <- col_to_convert$col[i]
colnum <- which(colnames(df) == colname)
for (j in 1:nrow(df))
{
df[j,colnum] <- as.numericdf(df[j,colnum])
}
}
Ce n'est pas idéal pour les grandes tables, car cela va cellule par cellule, mais cela ferait le travail.
Vous pouvez utiliser convert à partir du paquet hablar:
library(dplyr)
library(hablar)
# Sample df (stolen from the solution by Luca Braglia)
df <- tibble("a" = as.character(0:5),
"b" = paste(0:5, ".1", sep = ""),
"c" = letters[1:6])
# insert variable names in num()
df %>% convert(num(a, b))
Ce qui vous donne:
# A tibble: 6 x 3
a b c
<dbl> <dbl> <chr>
1 0. 0.100 a
2 1. 1.10 b
3 2. 2.10 c
4 3. 3.10 d
5 4. 4.10 e
6 5. 5.10 f
Si vous êtes paresseux, laissez retype () de hablar deviner le type de données souhaité:
df %>% retype()
ce qui vous donne:
# A tibble: 6 x 3
a b c
<int> <dbl> <chr>
1 0 0.100 a
2 1 1.10 b
3 2 2.10 c
4 3 3.10 d
5 4 4.10 e
6 5 5.10 f
comme ça?
DF <- data.frame("a" = as.character(0:5),
"b" = paste(0:5, ".1", sep = ""),
"c" = paste(10:15),
stringsAsFactors = FALSE)
DF <- apply(DF, 2, as.numeric)
S'il y a des "vrais" caractères dans le cadre de données comme "a" "b" "c", je recommanderais de répondre depuis davsjob.