Voici mon dataframe:
date ids
0 2011-04-23 [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13,...
1 2011-04-24 [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13,...
2 2011-04-25 [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13,...
3 2011-04-26 Nan
4 2011-04-27 [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13,...
5 2011-04-28 [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13,...
Je veux remplacer Nan
par []. Comment faire ça? Fillna ([]) n'a pas fonctionné. J'ai même essayé replace(np.nan, [])
mais cela donne une erreur:
TypeError('Invalid "to_replace" type: \'float\'',)
Vous pouvez d'abord utiliser loc
pour localiser toutes les lignes qui ont un nan
dans la colonne ids
, puis parcourir ces lignes en utilisant at
pour définir leurs valeurs à une liste vide:
for row in df.loc[df.ids.isnull(), 'ids'].index:
df.at[row, 'ids'] = []
>>> df
date ids
0 2011-04-23 [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13]
1 2011-04-24 [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13]
2 2011-04-25 [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13]
3 2011-04-26 []
4 2011-04-27 [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13]
5 2011-04-28 [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13]
Mon approche est similaire à celle de @ hellpanderrr, mais teste plutôt la liste plutôt que d'utiliser isnan
:
df['ids'] = df['ids'].apply(lambda d: d if isinstance(d, list) else [])
J'ai essayé à l'origine d'utiliser pd.isnull
(ou pd.notnull
) mais, quand on lui donne une liste, cela retourne la nullité de chaque élément.
Après beaucoup de grattage de tête, j'ai trouvé cette méthode qui devrait être la plus efficace (pas de boucle, pas d'application), en l'assignant simplement à une tranche:
isnull = df.ids.isnull()
df.loc[isnull, 'ids'] = [ [[]] * isnull.sum() ]
L'astuce consistait à construire votre liste de []
De la bonne taille (isnull.sum()
), et puis l'enfermer dans une liste: la valeur que vous affectez est un 2D tableau (1 colonne, isnull.sum()
lignes) contenant des listes vides comme éléments.
Sans affectations:
1) En supposant que nous n'avons que des flottants et des entiers dans notre trame de données
import math
df.apply(lambda x:x.apply(lambda x:[] if math.isnan(x) else x))
2) Pour toute trame de données
import math
def isnan(x):
if isinstance(x, (int, long, float, complex)) and math.isnan(x):
return True
df.apply(lambda x:x.apply(lambda x:[] if isnan(x) else x))
C'est probablement plus rapide, une solution de revêtement:
df['ids'].fillna('DELETE').apply(lambda x : [] if x=='DELETE' else x)
Peut-être plus dense:
df['ids'] = [[] if type(x) != list else x for x in df['ids']]
Une autre solution utilisant numpy:
df.ids = np.where(df.ids.isnull(), pd.Series([[]]*len(df)), df.ids)
Ou en utilisant combine_first:
df.ids = df.ids.combine_first(pd.Series([[]]*len(df)))