import numpy as np
import pandas as pd
import pandas_profiling as pdp
import matplotlib.pyplot as plt
%matplotlib inline
import seaborn as sns
import pickle
from sklearn.model_selection import train_test_split, GridSearchCV
from sklearn.preprocesing import MinMaxScaler
from sklearn.ensemble import RandomForestRegressor
from sklearn.metrics import r2_score
from sklearn.metrics import mean_squared_error
import xgboost as xgb
import lightgbm as lgb
import warnings
warnings.simplefilter('ignore')
with open ('imp_data.csv', mode='rb') as f:
imp_data=pickle.load(f)
with open('grid_rf_model.text', mode='rb') as f:
xgb_best_model=pickle.load(f)
with open('grid_gbm_model.text', mode='rb') as f:
gbm_best_model=pickle.load(f)
y_target = imp_data['price']
col=imp_data.columns.tolist()
col.remove['price']
x_explanatory=imp_data[col]
x_train, x_test, y_train, y_test =train_test_split(x_explanatory, y_target, random_state=1)
学習用データとテスト用データの偏りは出来るだけ抑える(値の分布を揃える)
ヒストグラムのチェック
fig=plt.figure(figuresize=(16,8))
ax1=fig.add_subplot(1,2,1)
plt.hist(y_train)
plt.title('train_data')
plt.xlabel('price')
plt.ylabel('frequency')
ax2 = fig.add_subplot(1,2,2)
plt.hist(y_test)
plt.title('test_data')
plt.xlabel('price')
plt.ylabel('frequency')
今回のケースでは、学習用とテスト用のデータの分布に大きな差異は見られませんでした。
発展的な内容になりますが、不均衡なデータに対する手法としては以下のようなものがあります。
アップサンプリング
ダウンサンプリング
損失関数の調整
これらを適応してみるとさらに精度が向上する可能性は十分にあります。
相関係数行列からの考察
一般的に説明変数を増やすほど決定係数が高くなりやすいため、分析者はついたくさんの説明変数を入れてしまいがちです。
しかし、相関が高すぎる値は機械学習モデルに対して悪影響を及ぼす可能性があります。(多重共線性)
plt.figure(figsize=(20,20))
corr=imp_data.corr()
cmap=sns.color_palette('coolwarm',200)
sns.heatmap(corr, xticklabel=corr.columns,
yticklabel=corr.columns,
square = True,
annot = True,
cmap=cmap)
plt.show()
imp_dataの相関係数の範囲は-0.42~0.45だったので、特に問題は無さそうですね。
※相関係数行列の対角成分は必ず1になるので、対角成分は除いて考えています。
feature_importanceからの考察
モデルを比較する際は数値のスケールをそろえる
scaler = MinMaxScaler()
fig= plt.figure(figsize=(16,16))
ax1=fig.add_subplot(2,2,1)
features = x_train.columns インデックスのリスト
importance = rf_best_model.feature_importances_
importances=importance/sum(importance)
indices=np.argsort(importances) importancesのソートされたリスト
plt.barh(range(len(indices)), importanes[indices], align='center')
plt.yticks(range(len(indices)), features[importances])
plt.title('RandomForest_importances')
plt.xlabel('importances')
plt.ylabel('features')
ax1.set_xlim(0,0.6)
ax2=fig.add_subplot(2,2,2)
features=x_train.columns
importance=xgb_best_model.feature_importances_
importances=importance/sum(importance)
indices=np.argsort(importances)
plt.barh(range(len(indices)),importances[indices], align='center')
plt.yticks(range(len(indices)), features[indices])
plt.title('XGboost_importances')
plt.xlabel('importances')
plt.ylabel('features')
ax2.set_xlim(0,0.6)
ax3=fig.add_subplot(2,2,3)
features=x_train.columns
importance=gbm_best_model.feature_importances_
importances=importance/sum(importance)
indices=np.argsort(importances) importanceの値そのもの
plt.barh(range(len(indices)),importance[indices], align='center')
plt.yticks(range(len(indices)),features[indices])
plt.title('LightGBM_importance')
plt.xlabel('importance')
plt.ylabel('feature')
ax3.set_xlim(0,0.6)
plt.show()
ランダムフォレスト:yearOfRegistrationを圧倒的に重視している
XGBoost:yearOfRegistrationを重視しつつ、他の変数も含めて総合的に予測している
LightGBM:PowerPSを重視しつつ、他の変数も含めて総合的に予測している
yearOfRegistrationとPowerPSはどのモデルでも重視されるという結果になっていますね。
コメント