Oregin
簡単な前処理(inning数、裏表列の追加、game_infoの結合,カテゴリカル変数のエンコーディング)を行ったサンプルコードです。ご参考までご活用ください。※Google Colabで実行可能です。※今回のタスクは、多値分類タスクなので、交差検証での予測値を平均ではなく、最頻値とすべきとのご指摘をいただき修正いたしました。
CV= 0.14017 LB= 0.13173 でした。
ディレクトリ構成
# xfeatのインストール !pip install git+https://github.com/pfnet-research/xfeat.git
# ------------------------------------------------------------------------------ # 各種ライブラリのインポート # ------------------------------------------------------------------------------ import pandas as pd import numpy as np import json import os import random import string import re from pathlib import Path from tqdm import tqdm import lightgbm as lgb from sklearn.model_selection import KFold from sklearn.metrics import f1_score from sklearn import preprocessing
# データ読み込み ##################################### ###### train ######################## ##################################### train = pd.read_csv('../data/train_data.csv') target = train['y'] train = train.drop(['id','y'],axis=1) ##################################### #### test ########################### ##################################### test = pd.read_csv('../data/test_data.csv') test = test.drop('id',axis=1) ##################################### #### test ########################### ##################################### game = pd.read_csv('../data/game_info.csv') game = game.drop('Unnamed: 0',axis=1)
# 訓練データのみにある列名(テストデータにはない列名)のリストを作成 delcollist = [] for col in train.columns: if not col in test.columns: delcollist.append(col) # 訓練データのみにある列名を削除 train = train.drop(delcollist,axis=1)
# inning を 数値に変換 train['inning_num'] = train['inning'].apply(lambda x: re.sub("\\D", "", x)) test['inning_num'] = test['inning'].apply(lambda x: re.sub("\\D", "", x))
# 表裏を判定する関数 def omote_ura(x): if '表' in x: return 0 else: return 1
# 表裏の列を追加 train['inning_ForB'] = train['inning'].apply(lambda x: omote_ura(x)) test['inning_ForB'] = test['inning'].apply(lambda x: omote_ura(x))
# game_infoの追加 train = pd.merge(train, game, how='left') test = pd.merge(test, game, how='left')
# inningの削除 train = train.drop('inning',axis=1) test = test.drop('inning',axis=1)
# カテゴリカル変数のカラムを抽出 categorical_columns = [x for x in train.columns if train[x].dtypes == 'object']
# カテゴリカル変数をカウントエンコードする from xfeat import CountEncoder encoder = CountEncoder(input_cols=categorical_columns) train = encoder.fit_transform(train) test = encoder.transform(test)
# 訓練データにターゲット列を追加する train['target'] = target
# カテゴリカル変数をターゲットエンコーディングする from sklearn.model_selection import KFold from xfeat import TargetEncoder fold = KFold(n_splits=5, shuffle=True, random_state=42) encoder = TargetEncoder(input_cols=categorical_columns, target_col='target', fold=fold) train = encoder.fit_transform(train) test = encoder.transform(test)
# エンコーディング前の列を削除する train = train.drop(categorical_columns,axis=1) test = test.drop(categorical_columns,axis=1)
train = train.drop('target',axis=1)
SEED = 42 NFOLDS = 5
#####################################################3 ### LGBで学習、予測する関数の定義 ######################################################## def Train_and_Pred(train,target,test): # -------------------------------------- # パラメータ定義 # -------------------------------------- lgb_params = { 'objective': 'multiclass', 'boosting_type': 'gbdt', 'n_estimators': 50000, 'colsample_bytree': 0.5, 'subsample': 0.5, 'subsample_freq': 3, 'reg_alpha': 8, 'reg_lambda': 2, 'random_state': SEED, "bagging_fraction": 0.5520399476847848, "bagging_freq": 1, "feature_fraction": 0.4436319472771827, "lambda_l1": 0.01113869595673112, "lambda_l2": 8.706009358617911e-07, "learning_rate": 0.012307412937706345, "min_child_samples": 18, "num_leaves": 8, } # -------------------------------------- # 学習と予測 # -------------------------------------- kf = KFold(n_splits=NFOLDS, shuffle=True, random_state=SEED) lgb_oof = np.zeros(train.shape[0]) lgb_pred = pd.DataFrame() for fold, (trn_idx, val_idx) in enumerate(kf.split(X=train)): X_train, y_train = train.iloc[trn_idx], target.iloc[trn_idx] X_valid, y_valid = train.iloc[val_idx], target.iloc[val_idx] X_test = test # LightGBM model = lgb.LGBMClassifier(**lgb_params) model.fit(X_train, y_train, eval_set=(X_valid, y_valid), eval_metric='logloss', verbose=False, early_stopping_rounds=500 ) lgb_oof[val_idx] = model.predict(X_valid) lgb_pred[f'fold_{fold}'] = model.predict(X_test) f1_macro = f1_score(y_valid, lgb_oof[val_idx], average='macro') print(f"fold {fold} lgb score: {f1_macro}") f1_macro = f1_score(target, lgb_oof, average='macro') print("+-" * 40) print(f"score: {f1_macro}") print(f"model score: {model.score(train, target)}") return f1_macro,lgb_pred
#学習と予測の実行 score,pred = Train_and_Pred(train,target,test)
# 予測値の最頻値を求める(ご指摘をいただき修正) sub_pred = pred.mode(axis=1)[0]
# ------------------------------------------------------------------------------ # 提出ファイルの作成 # ------------------------------------------------------------------------------ #テスト結果の出力 submit_df = pd.DataFrame({'y': sub_pred.astype(int)}) submit_df.index.name = 'id' submit_df.to_csv('submission.csv')