cross_entropy_error

#ロードバイク #山形

GoldenCheetah OpenDataを使って到達パワーを回帰予測してみる

ちょっと真面目にトレーニングをしているサイクリストなら、一度は使ったことがあるであろう「Golden Cheetah」プロジェクトが公開しているトレーニーのオープンデータを使用して、トレーニングによって期待できる最大パワーを予測してみました。という話です。

GoldenCheetah OpenDataとは

github.com

まぁ、詳しくは私も知らないので、(今回も結構趣味の遊びの範囲を出ませんし)githubを読んでみてほしいのですが、goldencheetahを使用しているトーレーニーの人たち(サイクリストだけでなく、トライアスリートも多めです。)のトレーニングデータがcsv形式で公開されているものです。 データは、各アクティビティデータもありますし、トレーニーごとのクリティカルパワー、体重なんかのプロフィールデータもあります。それぞれは個別IDで付番されているので、データの結合も容易でした。

20分間のクリティカルパワーを予測する回帰モデル

一昔前であれば、ローラー台でやるメニューと言えば20分走でした。個人的に興味のあるこの領域を予測できるモデルを目指します。 使用したデータは、GC OpenDataのathletes.csvです。このデータに入っているカラムはこんな感じでした。

import pandas as pd
athletes = pd.read_csv("athletes.csv")
print(athletes.columns)

Index(['id', 'age', 'gender', 'activities', 'bike', 'run', 'swim', 'other',
       '1s_critical_power', '15s_critical_power', '2m_critical_power',
       '3m_critical_power', '5m_critical_power', '8m_critical_power',
       '10m_critical_power', '20m_critical_power', '30m_critical_power',
       '1m_peak_wpk', '5m_peak_wpk', '10m_peak_wpk', '20m_peak_wpk',
       '30m_peak_wpk', '20s_peak', '20s_peak_wpk', '60s_peak', '60s_peak_wpk',
       '180s_peak', '180s_peak_wpk', '240s_peak', '240s_peak_wpk', '420s_peak',
       '420s_peak_wpk', '720s_peak', '720s_peak_wpk', 'weightkg',
       ' weightstd'],
      dtype='object')

***_critical_power 以降のデータはラン、スイムの指標なので、今回はあまり使わなくても良さそうです。逆に"weightkg"や"age"は経験則上かなり相関がありそうですが、各変数の寄与具合も気になるところです。

ここから、このデータをクレンジングする作業が続くわけですが、あくまでも個人的興味に基づく分析なので、年齢は18歳から60歳、体重は40kgから100kg、パワーも大きな外れ値(2000Wとか)は.loc[]で外していきました。 そんなこんなで解析にかけるデータ(具材)をちまちま用意して、scikit-learnで回帰予測をしてみます。

from sklearn import  linear_model
import sklearn.model_selection
model = linear_model.LinearRegression()
X = predict_data_rules[["age","bike","gender","5m_critical_power","10m_critical_power","weightkg"]]
y = predict_data_rules["20m_critical_power"]
X_train,X_test,y_train,y_test = sklearn.model_selection.train_test_split(X,y)
model.fit(X_train,y_train)
rider = [30,600,1,300,300,70] #年齢、練習回数、男女、5分最大パワー、10分最大パワー、体重から、20分最大パワーを回帰予測する
pred = [rider]
print("期待できる20分最大パワー:", model.predict(pred).round(2))

期待できる20分最大パワー: [292.89]

10分のクリティカルパワーの寄与が大きすぎるので、月の練習時間や距離なんかも加えるともっと良いモデルになると思います。

それにしても、この設定値はおおよそ私のベストな数値を入れてみたのですが、出力された期待できるパワーが292Wというのは、確かにこれまで調子いいときに出せてたくらいの数値です。

もう少し解析するデータを整えれば、トレーニングを行う上での改善指標が明確にできるかもしれませんね。