2017-08-20 3 views
0

Mon échantillon df a quatre colonnes avec NaN valeurs. L'objectif est de concaténer toutes les lignes tout en excluant les valeurs NaN.Combiner plusieurs colonnes dans Pandas à l'exclusion de NaNs

import pandas as pd 
import numpy as np 

df = pd.DataFrame({'keywords_0':["a", np.nan, "c"], 
       'keywords_1':["d", "e", np.nan], 
       'keywords_2':[np.nan, np.nan, "b"], 
       'keywords_3':["f", np.nan, "g"]}) 

    keywords_0 keywords_1 keywords_2 keywords_3 
0   a   d  NaN   f 
1  NaN   e  NaN  NaN 
2   c  NaN   b   g 

Vous voulez accomplir ce qui suit:

keywords_0 keywords_1 keywords_2 keywords_3 keywords_all 
0   a   d  NaN   f  a,d,f 
1  NaN   e  NaN  NaN   e 
2   c  NaN   b   g  c,b,g 

Code Pseudo:

cols = [df.keywords_0, df.keywords_1, df.keywords_2, df.keywords_3] 

df["keywords_all"] = df["keywords_all"].apply(lambda cols: ",".join(cols), axis=1) 

Je sais que je peux utiliser ",".join() pour obtenir le résultat exact, mais je ne suis pas sûr comment passer le noms de colonne dans la fonction.

Répondre

1

Vous pouvez appliquer ",".join() sur chaque ligne en transmettant axis=1 à la méthode d'application. Vous devez d'abord abandonner les NaN. Sinon, vous obtiendrez une erreur TypeError.

df.apply(lambda x: ','.join(x.dropna()), axis=1) 
Out: 
0 a,d,f 
1  e 
2 c,b,g 
dtype: object 

Vous pouvez attribuer ce retour à la trame de données d'origine avec

df["keywords_all"] = df.apply(lambda x: ','.join(x.dropna()), axis=1) 

Ou si vous souhaitez spécifier des colonnes que vous avez fait dans la question:

cols = ['keywords_0', 'keywords_1', 'keywords_2', 'keywords_3'] 
df["keywords_all"] = df[cols].apply(lambda x: ','.join(x.dropna()), axis=1) 
+0

pour votre dernière proposition, il a besoin de convertir Col. à '[ 'keywords_0', 'keywords_1', 'keywords_2' , 'keywords_3'] 'droite? –

+0

@RayhaneMama Oui, c'est vrai. J'ai fait confiance au pseudo code mais j'aurais dû être plus clair. Merci. – ayhan

+0

Merci. Cela a fonctionné avec brio! – cptpython

0

Il suffit de fournir une autre solution to_string:

df1[df1.isnull()]='' 
df1.apply(lambda x : x.to_string(index =False,na_rep=False),axis=1).replace({"\n":','},regex=True) 

Ensuite, il suffit assigner à votre colonne keywords_all en utilisant

df['keywords_all']=df1.apply(lambda x : x.to_string(index =False,na_rep=False),axis=1).replace({"\n":','},regex=True) 

ou

df.assign(keywords_all=df1.apply(lambda x : x.to_string(index =False,na_rep=False),axis=1).replace({"\n":','},regex=True) 
) 

Out[397]: 
    keywords_0 keywords_1 keywords_2 keywords_3 keywords_all 
0   a   d  NaN   f  a,d,f 
1  NaN   e  NaN  NaN   e 
2   c  NaN   b   g  b,c,g