목록 Python / NumPy에서 Nan을 제거하려면 어떻게해야합니까?


89

값을 계산하는 목록이 있는데, 내가 얻은 값 중 하나는 'nan'입니다.

countries= [nan, 'USA', 'UK', 'France']

제거하려고했지만 매번 오류가 발생합니다.

cleanedList = [x for x in countries if (math.isnan(x) == True)]
TypeError: a float is required

내가 이것을 시도했을 때 :

cleanedList = cities[np.logical_not(np.isnan(countries))]
cleanedList = cities[~np.isnan(countries)]

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''

4
"nan"실제 NaN 값이 아닌 문자열처럼 보입니다 .
BrenBarn 2014 년

1
네, 문자열입니다. [x for x in countries in x! = 'nan']
MarshalSHI

4
if condition == True불필요합니다 if condition. 언제든지 .
reem

지금까지 제공된 솔루션이 만족스럽지 않습니다. 나도 같은 문제를 안고있어. 기본적으로 문자열에는 작동하지 않습니다. 따라서 귀하의 경우 np.isnan('USA')동일한 오류 메시지를 보냅니다. 해결책을 찾으면 업로드하겠습니다.
Yohan Obadia

답변:


127

질문이 변경되었으므로에 대한 답이 있습니다.

math.isnanfloat 인수를 예상 하므로 문자열을 사용하여 테스트 할 수 없습니다 . 당신에 countries목록, 당신은 수레와 문자열을 가지고있다.

귀하의 경우 다음 사항으로 충분합니다.

cleanedList = [x for x in countries if str(x) != 'nan']

이전 답변

당신에 countries목록, 리터럴은 'nan'문자열이 아닌 파이썬 부동입니다 nan동일합니다 :

float('NaN')

귀하의 경우 다음 사항으로 충분합니다.

cleanedList = [x for x in countries if x != 'nan']

1
논리적으로 당신이 말하는 것은 사실입니다. 그러나 그것은 나에게 잘 풀리지 않았습니다.
user3001937

그런 다음 문제는 다른 영역에 있으며, 제공 한 배열은 math.isnan오류를 통해 자연스럽게 될 문자열 입니다.

예 ! 출력을 인쇄 할 때 다음과 같이 표시됩니다. [nan, 'USA', 'UK', 'France']
user3001937

1
@ user3001937 나는 새로운 정보를 기반으로 답변을 업데이 트했습니다

2
zhangxaochen : 그것은 문자열이 아니라 float입니다. 업데이트 된 답변을주의 깊게 살펴보십시오. Lego Stormtroopr가 x문자열 로 변환 하여 비교할 수 있습니다. 와 비교할 때에도 nan항상에 대해 false를 반환 하므로 ==비교 nan하는 가장 쉬운 방법입니다.
무료 Monica Cellio 2014.01.09

17

문제는 np.isnan()문자열 값을 올바르게 처리하지 못하기 때문에 발생 합니다. 예를 들어 다음과 같은 경우 :

np.isnan("A")
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''

그러나 pandas 버전 pd.isnull()은 숫자 및 문자열 값에 대해 작동합니다.

pd.isnull("A")
> False

pd.isnull(3)
> False

pd.isnull(np.nan)
> True

pd.isnull(None)
> True

14

귀하의 예를 사용하여 ...

countries= [nan, 'USA', 'UK', 'France']

nan은 nan (nan! = nan)과 같지 않고 countries [0] = nan이므로 다음 사항을 준수해야합니다.

countries[0] == countries[0]
False

하나,

countries[1] == countries[1]
True
countries[2] == countries[2]
True
countries[3] == countries[3]
True

따라서 다음이 작동합니다.

cleanedList = [x for x in countries if x == x]

1
이것은 문자열 목록에 float ( 'nan')이있을 때 작동하는 유일한 대답입니다.
kmundnic

12
import numpy as np

mylist = [3, 4, 5, np.nan]
l = [x for x in mylist if ~np.isnan(x)]

모든 NaN을 제거해야합니다. 물론 여기에서는 문자열이 아니라 실제 NaN ( np.nan) 이라고 가정합니다 .


1
이로 인해 오류가 발생합니다. TypeError : ufunc 'isnan'은 입력 유형에 대해 지원되지 않으며 캐스팅 규칙 ''safe ''
Zak Keirn

1
간단하지 않은 이유 : x[~ np.isnan(x)]? numpy에는 목록 이해가 필요하지 않습니다. 물론 x가 numpy 배열이라고 가정합니다.
bue

질문이 제안한 것처럼 x가 numpy 배열이 아닐 것이라고 가정했습니다.
Ajay Shah

float가 예상됩니다. @ZakKeirn
Shirish Bajpai


5

요소 유형을 확인하면

type(countries[1])

결과는 <class float> 다음 코드를 사용할 수 있습니다.

[i for i in countries if type(i) is not float]

4

다음과 같이 목록에서 누락 된 값을 제거하고 싶습니다.

list_no_nan = [x for x in list_with_nan if pd.notnull(x)]

1

귀하의 예에서는 'nan'문자열이므로 문자열을 isnan()확인하는 대신

이렇게 :

cleanedList = [x for x in countries if x != 'nan']

0

이를 수행하는 또 다른 방법은 다음 과 같은 필터를 사용하는 것입니다 .

countries = list(filter(lambda x: str(x) != 'nan', countries))

-1

예를 들어 Pandas는 빈 값에 대해 'nan'을 반환합니다. 문자열이 아니기 때문에 일치하려면 문자열로 변환해야합니다. 예를 들면 :

ulist = df.column1.unique() #create a list from a column with Pandas which 
for loc in ulist:
    loc = str(loc)   #here 'nan' is converted to a string to compare with if
    if loc != 'nan':
        print(loc)
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.