이번에는 꾸준하게 일주일에 하나씩 작성하는 걸 목표로 Velog를 시작해보려고 합니다!
첫 게시물의 주제는 Kaggle의 Child Mind Institute 데이터를 이용한 예측 모델 개발입니다. 😊
본 캐글 Competition의 주 목적은 아동 및 청소년의 신체 활동 데이터를 활용하여 문제적 인터넷 사용 수준을 예측하는 모델을 개발하는 것입니다.
Competition에서 사용할 데이터는 테이블 형태로 제공되며, 이를 바탕으로 분석을 진행할 예정입니다. 🔍
간략한 데이터 설명 후 EDA(탐색적 데이터 분석) 과정으로 넘어가 보겠습니다!
먼저 본 Competition의 평가 방식이 다소 독특하기 때문에, 평가 방식을 먼저 설명하겠습니다. 📈
QWK는 예측값과 실제값 간의 일치도를 평가하는 지표로, 0에서 1 사이의 값을 가집니다.
이 지표는 다음과 같이 해석됩니다:
QWK를 계산하려면 세 가지 행렬이 필요합니다: 관찰 행렬 (O), 가중치 행렬 (W), 기대 행렬 (E)입니다. 각 행렬에 대해 자세히 설명해보겠습니다.
예를 들어, 실제 레이블이 ([1, 2, 2, 3])이고 예측 레이블이 ([1, 2, 3, 3])이라면, 관찰 행렬 ( O )는 다음과 같습니다:
각 요소는 실제와 예측 레이블 간의 일치도를 표시하는 빈도수입니다.
여기서 ( i )와 ( j )는 레이블 값이고, ( N )은 레이블의 개수입니다.
예를 들어, ( N = 4 )일 경우 ( W )는 다음과 같습니다:
이 행렬에서는 예측과 실제의 차이가 클수록 가중치가 더 크게 적용됩니다. 📉
예를 들어, 실제 레이블의 히스토그램이 ([2, 1, 1])이고 예측 레이블의 히스토그램이 ([1, 2, 1])이라면, 기대 행렬 ( E )는 다음과 같습니다:
이제 세 개의 행렬 ( O ), ( W ), ( E )가 준비되었으므로, 아래 공식을 통해 QWK를 계산할 수 있습니다:
이제 평가지표를 정리했으니, 본격적으로 EDA 과정에 들어가겠습니다! 🔍
이 EDA 과정에서는 sii에 따라 PCIAT-PCIAT_Total 값의 최소값과 최대값을 구하고, sii 값이 있는 데이터를 필터링하여 누락된 값을 시각적으로 확인했습니다. 또한 PCIAT-PCIAT_Total이 개별 PCIAT 항목들의 합으로 올바르게 계산되었는지를 검토하였습니다.
agg() 함수를 사용한 그룹별 최소 및 최대값 구하기pciat_min_max = train.groupby('sii')['PCIAT-PCIAT_Total'].agg(['min','max'])
pciat_min_max = pciat_min_max.rename(
columns = {'min' : 'Minimun PCIAT total Score', 'max' : 'Maximum total PCIAT Score'})
pciat_min_max
train 데이터에서 sii 값에 따라 PCIAT-PCIAT_Total 값의 최소값과 최대값을 그룹별로 구하는 과정입니다. agg(['min', 'max'])를 사용하여 min과 max 값을 동시에 구할 수 있습니다..rename()을 통해 열 이름을 직관적으로 변경하여, Minimum PCIAT total Score와 Maximum total PCIAT Score로 구분하여 분석을 진행했습니다.notna()를 사용하여 sii 값이 있는 데이터 필터링하기 📋train_with_sii = train[train['sii'].notna()][columns_not_in_test] # ~isna() == notna()
~data['컬럼명'].isna()를 통해 NaN이 아닌 값을 필터링했지만, 여기서는 notna()를 사용하여 한 번에 해당 작업을 처리할 수 있음을 알게 되었습니다.notna()는 isna()와 반대로 동작하여, NaN이 아닌 값들만 선택할 수 있게 합니다.style.applymap()을 사용하여 누락된 값 시각적으로 강조하기 🌸train_with_sii[train_with_sii.isna().any(axis=1)].head().style.applymap(
lambda x: 'background-color: #FFC0CB' if pd.isna(x) else ''
)
style.applymap()을 사용해 NaN 값이 있는 셀에 배경색을 적용하여 시각적으로 강조할 수 있습니다. NaN 값인 경우 #FFC0CB 색상(핑크색)을 배경으로 지정하였고, 그렇지 않으면 아무 색상도 적용되지 않도록 하였습니다.sum()을 사용하여 PCIAT 항목의 합이 총점과 일치하는지 확인하기 ✔️PCIAT
_cols = [f'PCIAT-PCIAT_{i+1:02d}' for i in range(20)]
recalc_total_score = train_with_sii[PCIAT_cols].sum(axis=1, skipna=True)
(recalc_total_score == train_with_sii['PCIAT-PCIAT_Total']).all() # PCIAT Values Sum == Total
sum(axis=1, skipna=True)는 NaN 값을 무시하고 각 행을 기준으로 합계를 계산합니다. 이 코드는 PCIAT-PCIAT_Total이 실제로 개별 항목들의 합과 동일하게 계산되었는지 확인하는 과정입니다.(recalc_total_score == train_with_sii['PCIAT-PCIAT_Total']).all()을 사용해 계산된 총합과 PCIAT-PCIAT_Total의 값이 모두 일치하는지 확인합니다.위의 코드를 통해 pandas에서 제공하는 agg, notna, applymap과 같은 다양한 기능을 활용하여 데이터의 특정 부분을 필터링하거나 시각적으로 강조할 수 있음을 알게 되었어요. 특히 notna() 함수는 기존에 ~data['컬럼명'].isna()와 같은 방식 대신 간결하게 사용할 수 있어 유용했고, 평소 Pandas를 자주 사용해서 쉽게 접근했지만 하나하나 진행하며 코드를 익히는 시간이 될 거 같다는 생각이 들었어요 오늘 EDA는 여기까지~😊