J'ai un problème de classification en machine learning avec 80% de variables catégorielles. Dois-je utiliser un encodage à chaud si je veux utiliser un classificateur pour la classification? Puis-je transmettre les données à un classificateur sans encodage?
J'essaie de faire ce qui suit pour la sélection des fonctionnalités:
J'ai lu le fichier du train:
num_rows_to_read = 10000 train_small = pd.read_csv("../../dataset/train.csv", nrows=num_rows_to_read)
Je change le type des caractéristiques catégorielles en 'catégorie':
non_categorial_features = ['orig_destination_distance', 'srch_adults_cnt', 'srch_children_cnt', 'srch_rm_cnt', 'cnt'] for categorical_feature in list(train_small.columns): if categorical_feature not in non_categorial_features: train_small[categorical_feature] = train_small[categorical_feature].astype('category')
J'utilise un encodage à chaud:
train_small_with_dummies = pd.get_dummies(train_small, sparse=True)
Le problème est que la 3ème partie reste souvent bloquée, même si j'utilise une machine puissante.
Ainsi, sans le seul encodage à chaud, je ne peux pas faire de sélection de fonctionnalités, pour déterminer l'importance des fonctionnalités.
Que recommandez-vous?
drop_first=True
avecget_dummies
supprime la nécessité de supprimer la colonne d'origine séparémentBeaucoup plus facile à utiliser Pandas pour l'encodage de base à chaud. Si vous recherchez plus d'options, vous pouvez utiliser
scikit-learn
.Pour l'encodage à chaud de base avec Pandas, il vous suffit de passer votre trame de données dans la fonction get_dummies .
Par exemple, si j'ai un dataframe appelé imdb_movies :
... et je veux encoder à chaud la colonne Notée, je fais simplement ceci:
Cela renvoie un nouveau
dataframe
avec une colonne pour chaque " niveau " de notation qui existe, avec un 1 ou un 0 spécifiant la présence de cette note pour une observation donnée.Habituellement, nous voulons que cela fasse partie de l'original
dataframe
. Dans ce cas, nous attachons simplement notre nouveau cadre codé factice sur le cadre d'origine en utilisant " column-binding .Nous pouvons lier des colonnes à l'aide de la fonction concat de Pandas :
Nous pouvons maintenant exécuter une analyse sur notre pleine
dataframe
.FONCTION UTILITAIRE SIMPLE
Je recommanderais de vous créer une fonction utilitaire pour le faire rapidement:
Utilisation :
Résultat :
De plus, selon le commentaire @pmalbu, si vous souhaitez que la fonction supprime le feature_to_encode d'origine, utilisez cette version:
Vous pouvez encoder plusieurs entités en même temps comme suit:
la source
Vous pouvez le faire avec
numpy.eye
et a en utilisant le mécanisme de sélection des éléments du tableau:La valeur de retour de
indices_to_one_hot(nb_classes, data)
est maintenantLe
.reshape(-1)
est là pour vous assurer que vous avez le bon format d'étiquettes (vous pourriez aussi avoir[[2], [3], [4], [0]]
).la source
Tout d'abord, le moyen le plus simple de coder à chaud: utilisez Sklearn.
http://scikit-learn.org/stable/modules/generated/sklearn.preprocessing.OneHotEncoder.html
Deuxièmement, je ne pense pas que l'utilisation de pandas pour un encodage à chaud soit aussi simple (non confirmé cependant)
Création de variables factices dans Pandas pour Python
Enfin, est-il nécessaire de faire un encodage à chaud? Un encodage à chaud augmente de manière exponentielle le nombre de fonctionnalités, augmentant considérablement le temps d'exécution de tout classificateur ou de tout autre élément que vous allez exécuter. Surtout lorsque chaque caractéristique catégorielle a plusieurs niveaux. Au lieu de cela, vous pouvez effectuer un codage factice.
L'utilisation d'un codage factice fonctionne généralement bien, pour beaucoup moins de temps d'exécution et de complexité. Un prof avisé m'a dit un jour: «Moins c'est plus».
Voici le code de ma fonction d'encodage personnalisée si vous le souhaitez.
EDIT: Comparaison pour être plus claire:
Encodage à chaud: convertissez n niveaux en n-1 colonnes.
Vous pouvez voir comment cela fera exploser votre mémoire si vous avez de nombreux types (ou niveaux) différents dans votre fonction catégorielle. Gardez à l'esprit que ce n'est qu'une colonne.
Codage factice:
Convertissez plutôt en représentations numériques. Économise considérablement de l'espace sur les fonctionnalités, au prix d'un peu de précision.
la source
mouse > cat > dog
mais ce n'est pas le cas.get_dummies
est le moyen le plus simple de transférer des variables catégorielles dans des données conviviales pour les modèles de mon expérience (bien que très limité)Un encodage à chaud avec des pandas est très simple:
ÉDITER:
Une autre façon de one_hot en utilisant sklearn
LabelBinarizer
:la source
Vous pouvez utiliser la fonction numpy.eye.
Résultat
la source
pandas comme a la fonction intégrée "get_dummies" pour obtenir un encodage à chaud de cette colonne / s particulière.
code d'une ligne pour un encodage à chaud:
la source
Voici une solution utilisant
DictVectorizer
et laDataFrame.to_dict('records')
méthode Pandas .la source
Le codage à chaud nécessite un peu plus que la conversion des valeurs en variables indicatrices. En règle générale, le processus de ML vous oblige à appliquer ce codage plusieurs fois à des ensembles de données de validation ou de test et à appliquer le modèle que vous construisez à des données observées en temps réel. Vous devez stocker le mappage (transformation) qui a été utilisé pour construire le modèle. Une bonne solution utiliserait le
DictVectorizer
ouLabelEncoder
(suivi deget_dummies
. Voici une fonction que vous pouvez utiliser:Cela fonctionne sur une trame de données pandas et pour chaque colonne de la trame de données, il crée et renvoie un mappage. Donc, vous l'appelleriez comme ceci:
Puis sur les données de test, l'appel se fait en passant le dictionnaire renvoyé par l'entraînement:
Une méthode équivalente consiste à utiliser
DictVectorizer
. Un article connexe sur le même est sur mon blog. Je le mentionne ici car il fournit un raisonnement derrière cette approche sur l'utilisation simple du post get_dummies (divulgation: c'est mon propre blog).la source
Vous pouvez transmettre les données au classificateur catboost sans codage. Catboost gère lui-même les variables catégorielles en effectuant un codage de moyenne expansible one-hot et target.
la source
Vous pouvez également effectuer les opérations suivantes. Remarque pour ce qui suit, vous ne devez pas utiliser
pd.concat
.Vous pouvez également remplacer les colonnes explicites par catégorielles. Par exemple, ici je change le
Color
etGroup
la source
Je sais que je suis en retard à cette fête, mais le moyen le plus simple d'encoder à chaud une trame de données de manière automatisée est d'utiliser cette fonction:
la source
J'ai utilisé ceci dans mon modèle acoustique: cela aide probablement dans votre modèle.
la source
Pour ajouter à d'autres questions, laissez-moi vous expliquer comment je l'ai fait avec une fonction Python 2.0 utilisant Numpy:
La ligne
n_values = np.max(y_) + 1
pourrait être codée en dur pour que vous utilisiez le bon nombre de neurones au cas où vous utiliseriez des mini-lots par exemple.Projet de démonstration / tutoriel où cette fonction a été utilisée: https://github.com/guillaume-chevalier/LSTM-Human-Activity-Recognition
la source
Cela fonctionne pour moi:
Production:
la source
Cela peut et devrait être aussi simple que:
Utilisation:
la source
Élargir la réponse de @Martin Thoma
la source
Réponse courte
Voici une fonction pour effectuer un encodage à chaud sans utiliser numpy, pandas ou autres packages. Il prend une liste d'entiers, de booléens ou de chaînes (et peut-être d'autres types aussi).
Exemple:
Réponse longue (er)
Je sais qu'il y a déjà beaucoup de réponses à cette question, mais j'ai remarqué deux choses. Premièrement, la plupart des réponses utilisent des packages comme numpy et / ou pandas. Et c'est une bonne chose. Si vous écrivez du code de production, vous devriez probablement utiliser des algorithmes robustes et rapides comme ceux fournis dans les packages numpy / pandas. Mais, dans un souci d'éducation, je pense que quelqu'un devrait fournir une réponse qui a un algorithme transparent et pas seulement une implémentation de l'algorithme de quelqu'un d'autre. Deuxièmement, j'ai remarqué que de nombreuses réponses ne fournissent pas une implémentation robuste de l'encodage à chaud car elles ne répondent pas à l'une des exigences ci-dessous. Voici quelques-unes des exigences (telles que je les vois) pour une fonction d'encodage à chaud utile, précise et robuste:
Une fonction d'encodage à chaud doit:
J'ai testé de nombreuses réponses à cette question et la plupart d'entre elles échouent à l'une des exigences ci-dessus.
la source
Essaye ça:
df_encoded.head ()
La trame de données résultante
df_train_encoded
est la même que l'original, mais les fonctionnalités catégorielles sont désormais remplacées par leurs versions encodées à chaud.Plus d'informations
category_encoders
ici .la source
Ici, j'ai essayé avec cette approche:
la source