데이터프레임에는 원소 데이터 값이 종종 누락되는 경우가 있다. 데이터를 파일로 입력할 때 빠트리거나 파일 형식을 변환하는 과정에서 데이터가 소실되는 것이 주요 원인이다. 일반적으로 유효한 데이터 값이 존재하지 않는 누락 데이터를 NaN(Not a Number)으로 표시한다.

머신러닝 분석 모형에 데이터를 입력하기 전에 반드시 누락 데이터를 제거하거나 다른 적절한 값으로 대체하는 과정이 필요하다. 누락 데이터가 많아지면 데이터의 품질이 떨어지고, 머신러닝 분석 알고리즘을 왜곡하는 현상이 발생하기 떄문이다.

누락 데이터가 NaN으로 표시되지 않을 경우

누락 데이터가 NaN으로 입력되지 않고 '-', '?' 등의 ㅣ문자로 입력되기도 한다. 이때 replace() 메서드를 이용해서 Numpy의 np.nan으로 변경해줘야 한다.

df.replace('?', np.nan, inplace = True)

누락 데이터 확인

데이터셋을 불러오고 누락된 데이터가 있는지 info()로 확인해보자.

import matplotlib.pyplot as plt
import seaborn as sns

df = sns.load_dataset('titanic')
print(df.info())
<class 'pandas.core.frame.DataFrame'>
RangeIndex: 891 entries, 0 to 890
Data columns (total 15 columns):
 #   Column       Non-Null Count  Dtype
---  ------       --------------  -----
 0   survived     891 non-null    int64
 1   pclass       891 non-null    int64
 2   sex          891 non-null    object
 3   age          714 non-null    float64
 4   sibsp        891 non-null    int64
 5   parch        891 non-null    int64
 6   fare         891 non-null    float64
 7   embarked     889 non-null    object
 8   class        891 non-null    category
 9   who          891 non-null    object
 10  adult_male   891 non-null    bool
 11  deck         203 non-null    category
 12  embark_town  889 non-null    object
 13  alive        891 non-null    object
 14  alone        891 non-null    bool
dtypes: bool(2), category(2), float64(2), int64(4), object(5)
memory usage: 80.7+ KB
None

RangeIndex를 보면 각 열에 891개의 데이터가 있다는 것을 알 수 있다. 그리고 'deck'열에는 non-null(유효한) 데이터가 203개가 있다. 이는 누락된 데이터가 891 - 203 = 688개 라는 것을 알 수 있다.

value_counts(dropna = False)로 확인할 수 도 있다.

import matplotlib.pyplot as plt
import seaborn as sns

df = sns.load_dataset('titanic')
print(df['deck'].value_counts(dropna=False))
NaN    688
C       59
B       47
D       33
E       32
A       15
F       13
G        4
Name: deck, dtype: int64

isnull(), notnull() : 누락데이터 직접찾기

import matplotlib.pyplot as plt
import seaborn as sns

df = sns.load_dataset('titanic')

print(df.head().isnull())
print("--------------------------\\n")
print(df.head().notnull())
	 survived  pclass    sex  ...  embark_town  alive  alone
0     False   False  False  ...        False  False  False
1     False   False  False  ...        False  False  False
2     False   False  False  ...        False  False  False
3     False   False  False  ...        False  False  False
4     False   False  False  ...        False  False  False

[5 rows x 15 columns]
--------------------------

   survived  pclass   sex  ...  embark_town  alive  alone
0      True    True  True  ...         True   True   True
1      True    True  True  ...         True   True   True
2      True    True  True  ...         True   True   True
3      True    True  True  ...         True   True   True
4      True    True  True  ...         True   True   True

[5 rows x 15 columns]