Numpy isnan () échoue sur un tableau de flottants (à partir de pandas dataframe s'appliquent)


101

J'ai un tableau de flotteurs (certains nombres normaux, certains nans) qui sortent d'une application sur un dataframe pandas.

Pour une raison quelconque, numpy.isnan échoue sur ce tableau, mais comme indiqué ci-dessous, chaque élément est un flottant, numpy.isnan s'exécute correctement sur chaque élément, le type de la variable est définitivement un tableau numpy.

Que se passe-t-il?!

set([type(x) for x in tester])
Out[59]: {float}

tester
Out[60]: 
array([-0.7000000000000001, nan, nan, nan, nan, nan, nan, nan, nan, nan,
   nan, nan, nan, nan, nan, nan, nan, nan, nan, nan, nan, nan, nan,
   nan, nan, nan, nan, nan, nan, nan, nan, nan, nan, nan, nan, nan,
   nan, nan, nan, nan, nan, nan, nan, nan, nan, nan, nan, nan, nan,
   nan, nan], dtype=object)

set([type(x) for x in tester])
Out[61]: {float}

np.isnan(tester)
Traceback (most recent call last):

File "<ipython-input-62-e3638605b43c>", line 1, in <module>
np.isnan(tester)

TypeError: ufunc 'isnan' not supported for the input types, and the inputs could not be safely coerced to any supported types according to the casting rule ''safe''

set([np.isnan(x) for x in tester])
Out[65]: {False, True}

type(tester)
Out[66]: numpy.ndarray

Réponses:


163

np.isnan peut être appliqué aux tableaux NumPy de type dtype natif (comme np.float64):

In [99]: np.isnan(np.array([np.nan, 0], dtype=np.float64))
Out[99]: array([ True, False], dtype=bool)

mais lève TypeError lorsqu'il est appliqué aux tableaux d'objets:

In [96]: np.isnan(np.array([np.nan, 0], dtype=object))
TypeError: ufunc 'isnan' not supported for the input types, and the inputs could not be safely coerced to any supported types according to the casting rule ''safe''

Puisque vous avez Pandas, vous pouvez utiliser à la pd.isnullplace - il peut accepter des tableaux NumPy d'objets ou de types natifs:

In [97]: pd.isnull(np.array([np.nan, 0], dtype=float))
Out[97]: array([ True, False], dtype=bool)

In [98]: pd.isnull(np.array([np.nan, 0], dtype=object))
Out[98]: array([ True, False], dtype=bool)

Notez que cela Noneest également considéré comme une valeur nulle dans les tableaux d'objets.


3
Merci - utilisé pd.isnull (). Ne semble pas non plus avoir d'impact sur les performances.
tim654321

11

Un excellent substitut à np.isnan () et pd.isnull () est

for i in range(0,a.shape[0]):
    if(a[i]!=a[i]):
       //do something here
       //a[i] is nan

puisque seul nan n'est pas égal à lui-même.


cela peut ne pas fonctionner pour les tableaux car il déclenche le bien connu "ValueError: La valeur de vérité d'un xxx est ambiguë".
MSeifert

@MSeifert Parlez-vous de python ? J'utilise simplement cette méthode pour faire quelque chose dans l'apprentissage automatique, pourquoi je n'ai pas rencontré l'erreur bien connue?
Statham

Oui, il semble que vous n'ayez jamais utilisé numpy ou pandas auparavant. Utilisez import numpy as np; a = np.array([1,2,3, np.nan])et exécutez simplement votre code.
MSeifert

@MSeifert euh, je suis nouveau sur numpy mais le code a fonctionné correctement, aucune erreur ne s'est produite
Statham

Dans [1]: importez numpy as np Dans [2]: a = np.array ([1,2,3, np.nan]) Dans [3]: affichez un [1. 2. 3. nan] In [ 4]: print a [3] == a [3] False
Statham

10

En plus de la réponse @unutbu, vous pouvez forcer le tableau d'objets numpy pandas au type natif (float64), quelque chose le long de la ligne

import pandas as pd
pd.to_numeric(df['tester'], errors='coerce')

Spécifiez errors = 'contraindre' pour forcer les chaînes qui ne peuvent pas être analysées à une valeur numérique à devenir NaN. Le type de colonne serait dtype: float64, puis la isnanvérification devrait fonctionner


Son nom semble être unutbu;)
Dr_Zaszuś

@ Dr_Zaszuś Merci, corrigé
Severin Pappadeux

0

Assurez-vous d'importer le fichier csv à l'aide de Pandas

import pandas as pd

condition = pd.isnull(data[i][j])
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.