2015-08-05 2 views
2

У меня есть следующий панда Dataframe с NaN в нем.pandas проверка для nan не работает с использованием .isin()

import pandas as pd 
df = pd.DataFrame([1,2,3,float('nan')], columns=['A']) 
df 

    A 
0 1 
1 2 
2 3 
3 NaN 

У меня также есть список filter_list с помощью которой я хочу, чтобы фильтровать мой Dataframe. Но если я использую функцию .isin(), она не обнаруживает NaN. Вместо того, чтобы True я получаю False в последней строке

filter_list = [1, float('nan')] 

df['A'].isin(filter_list) 
0  True 
1 False 
2 False 
3 False 
Name: A, dtype: bool 

Ожидаемый результат:

0  True 
1 False 
2 False 
3 True 
Name: A, dtype: bool 

Я знаю, что я могу использовать .isnull() для проверки NaNs. Но здесь у меня есть и другие ценности, которые нужно проверить. Я использую pandas 0.16.0 версия

Редактировать: Список filter_list исходит от пользователя. Таким образом, он может иметь или не иметь NaN. Вот почему я использую .isin()

+0

Это не сработает, потому что 'np' использует тот факт, что' NaN! = NaN', поэтому это не удается, поэтому сначала вам нужно сначала фильтровать значения «NaN», а затем фильтровать другие значения – EdChum

+0

есть способ, которым я могу создать элемент 'NaN' в' filter_list', так что pandas это понимает? –

+1

Нет, я так не думаю, например 'df ['A'] == float ('nan')' все еще не работает, в нижней строке вам нужно использовать 'isnull' или' notnull' для тестирования 'NaN' правильно – EdChum

ответ

3

Вы могли бы заменить nan с уникальным не-NaN значения, которое не будет иметь место в списке, скажем, 'NA' или '' , Например:

In [23]: import pandas as pd 

In [24]: df = pd.DataFrame([1, 2, 3, pd.np.nan], columns=['A']) 

In [25]: filter_list = pd.Series([1, pd.np.nan]) 

In [26]: na_equiv = 'NA' 

In [27]: df['A'].replace(pd.np.nan, na_equiv).isin(filter_list.replace(pd.np.nan, na_equiv)) 
Out[27]: 
0  True 
1 False 
2 False 
3  True 
Name: A, dtype: bool 
3

Поплавок NaN обладает интересным свойством, что it is not equal to itself:

In [194]: float('nan') == float('nan') 
Out[194]: False 

isin проверки на равенство. Поэтому вы не можете использовать isin, чтобы проверить, соответствует ли значение NaN. Для проверки NaN лучше всего использовать np.isnull.


In [200]: df['A'].isin([1]) | df['A'].isnull() 
Out[200]: 
0  True 
1 False 
2 False 
3  True 
Name: A, dtype: bool 
+0

Проблема заключается в том, что список 'filter_list' исходит от пользователя. Таким образом, это может быть или не иметь «NaN» –

+1

Либо измените пользовательский интерфейс, чтобы «filter_nan» был дополнительным параметром, а NaN не включен в 'filter_list', иначе проверьте' pd.isnull (filter_list) .any() ' и обрабатывать дела соответственно. – unutbu

0

Если вы действительно что использовать isin(), чтобы соответствовать NaN. Вы можете создать класс, который имеет тот же хэш как нан и возвращает истину, если сравнить с нан:

import numpy as np 
import pandas as pd 

class NAN(object): 
    def __eq__(self, v): 
     return np.isnan(v) 

    def __hash__(self): 
     return hash(np.nan) 

nan = NAN() 

df = pd.DataFrame([1,2,3,float('nan')], columns=['A']) 
df.A.isin([1, nan]) 
Смежные вопросы