본문 바로가기
python/MLDL

캐글 Regression with an Abalone Dataset 도전 (1)

by 포잉띠 2024. 4. 24.

그간 간단한 이진분류, 다중분류 문제들만 접하다가 처음으로 연속적인 값을 예측해야 하는 문제를 접했다.

 

https://www.kaggle.com/competitions/playground-series-s4e4

 

Regression with an Abalone Dataset | Kaggle

 

www.kaggle.com

캐글 플레이그라운드 문제인데 기존 늘 하던것처럼 tfdf의 랜덤포레스트 모델부터 돌려봤다.

손실함수 값도, 정확도도 잘 학습되었다고는 볼 수 없었고, 예측을 출력하는것도 잘 안되었다.

예측 데이터의 차원때문에 계속해서 오류가 났는데  문제가 뭐일까 살펴보다가 로그가 기존 분류와는 다르게 위의 캡쳐 처럼 30개의 클래스별로 예측한 확률을 30개의 차원으로 출력을 해버려서 오류가 나지 않았나 싶다.

predictions_1 = predictions[:,1]

 

으로 첫번쨰 클래스를 확인해봤는데 다 0만 박혀있어서 깜짝 놀랐다.

가장 무난해 보이는 13~14번째 클래스도 확인해 보았는데 예측하고싶었던 Rings(나이) 와는 다르게 확률만 잔뜩 들어있었다...

array([0.01      , 0.        , 0.03      , 0.00333333, 0.06000001,
       0.00666667, 0.05      , 0.01333333, 0.02666667, 0.2133332 ,
       0.13666661, 0.02      , 0.01666667, 0.06666667, 0.07      ,
       0.07666666, 0.31666645, 0.11999995, 0.02333334, 0.06333334,
       0.27999982, 0.15999992, 0.09666664, 0.10999996, 0.18333323,
       0.09999997, 0.1899999 , 0.04      , 0.11333329, 0.03666667,
....

 

이상함을 감지하고 GPT의 도움을 받았다.

 

원인은 회귀문제를 분류모델에 집어넣어서 였다.

rf = tfdf.keras.RandomForestModel(hyperparameter_template="benchmark_rank1")
rf.compile(metrics=["acc"])
rf_his =rf.fit(x = train_ds, verbose=2)

이런식으로 그간 벤치마크가 높은 미리 어느정도 검증된 하이퍼파라미터 탬플릿을 사용했었다.

그래서 추가로 회귀를 지정해주거나 그런것 없이 데이터 모양새 보고 알아서 해주는 줄 알았다...

 

다행히? 아쉽게도? 그정도로 아직 컴퓨터가 똑똑하지는 않더라.

 

tfdf 랜덤포레스트 회귀버전 사용이 생각보다 어렵지 않았다.

model = tfdf.keras.RandomForestModel(task=tfdf.keras.Task.REGRESSION)

으로 모델을 생성하고

train_ds = tfdf.keras.pd_dataframe_to_tf_dataset(train_df, label="Rings", task=tfdf.keras.Task.REGRESSION)

기존 데이터프레임을 텐서플로우 데이터셋으로 변환하는 과정에 

task = tfdf.keras.Task.REGRESSION 을 추가해 주고

model.compile(metrics=["root_mean_squared_error"])
model_his =model.fit(x = train_ds, verbose=2)

이런식으로 모델 컴파일 할 때 metircs를 RMSE, 회귀 전용 metrics를 적어주면 된다고 한다.

다만 CNN 만들때 loss함수나 optimizer를 약자로 써도 되었는데 여기서는 안되는 듯 하다.

 

싸이킷런, sckit learn으로 진행하는 방법도 GPT 선생님이 친절히 알려주셨다.

from sklearn.ensemble import RandomForestRegressor

 

model = RandomForestRegressor(n_estimators=100,  # 트리의 수
                              random_state=42,    # 결과의 재현성을 위해
                              max_depth=None,     # 트리의 최대 깊이
                              min_samples_split=2,# 내부 노드를 분할하는데 필요한 최소 샘플 수
                              min_samples_leaf=1) # 리프 노드에 있어야 하는 최소 샘플 수
X = train_df.drop('{label}', axis=1)  # 'label'를 제외한 모든 열
y = train_df['{label}']               # 'label' 열

# X: 특성 배열 (2D array)
# y: 타겟 배열 (1D array)
model.fit(X, y) # 학습
predictions = model.predict(X_test)  # 새로운 데이터에 대한 예측

 

텐서플로우처럼 준비할게 많이 없어서 좋았다.

위의 과정으로 모델을 학습, 예측하고

from sklearn.metrics import mean_squared_error, mean_absolute_error
mse = mean_squared_error(y_test, predictions)
mae = mean_absolute_error(y_test, predictions)
rmse = mean_squared_error(y_test, predictions, squared=False)
print(f"MSE: {mse}, MAE: {mae}, RMSE: {rmse}")

이러한 코드로 모델을 평가 한다고 한다.

 

텐서플로우를 사용해도 비슷한 방법으로

import numpy as np
from sklearn.metrics import mean_squared_error

rmse = np.sqrt(mean_squared_error(y_test, predictions))
print(f"RMSE: {rmse}")

싸이킷런의 mse를 불러와서 평가를 진행하는 것 같다.

 

SQL만 하다가 간만에 머신러닝을 만지니까 행복하다. 재밌다.

아직 학습, 예측 제대로 된 것이 하나도 없는데도 말이다.

 

할 건 해야지...