stockedge.jpの技術メモ

http://stockedge.jp/の中の人が書いてる技術メモ

筋トレのモチベーションを上げるために使用重量の推移を予測した話

f:id:stockedge:20160305125058j:plain
たまには株や競馬以外の話題でも。


私は去年の6月から筋トレを始めた。筋トレには以下のようなメリットがあるからだ。

これだけのリターンをほぼノーリスクで得られる筋トレは恐らく最も投資効率が高い投資の一つ*1ではないかと思う。


とはいえこれらのメリットは、長期的にはこういうメリットが有るという話であって、短期的には変化が見えにくく、やりがいがない。
だから、できれば日々の成長を数値的に把握したい。そうすれば、成長している実感を感じられてモチベーションアップに繋がるかもしれない。

私は筋トレをやるたびに、何月何日に何キロを何回上げられたか記録を取っている。以下に私のプルオーバーの記録を載せておく*2。あらかじめ言っておくが誇れるような記録ではない。ガチ勢からは鼻で笑われるレベルのものだ。*3
プルオーバーの記録 · GitHub

「異時点間の記録の比較ができない」という問題

このデータを分析しようとすると、異時点間の記録の比較ができないという問題が立ちはだかる。
例えば、このデータでは、2015年9月20日に41キロを13回挙げて、その次の2015年9月27日には46キロを11回挙げている。しかし、41キロの重量を13回動かすのと、46キロの重量を11回動かすのでは、果たしてどちらの方が負担が大きいのだろうか? 回数では20日の記録が勝っているが、重量では27日の記録が勝っており、どちらの方が負荷が大きかったのかは分からない。
これらを適切に比較するためには、何らかの形で記録を変換する必要がありそうだ。
調べてみたところ、幸いにも、筋トレの記録を比較するための変換方法は既に確立されているらしい。以下がその論文である。
The Accuracy of Prediction Equations for Estimating 1-RM Performance in the Bench Press, Squat, and Deadlift
この論文曰く、ウェイトトレーナーの筋力を測定するとき、1-RM(one-repetition maximum、一回しか持ち上げることができない最大重量)という尺度がよく使われる。しかし1-RMは非常に重い重量を扱うので、危険性が高い。できることなら、もっと軽い重量を何回も持ち上げ、その記録から1-RMの重量を予測できると嬉しい。
そんなわけで、1-RMの重量を予測するための式は今までにいくつか考案されているようだ。その中で最も予測精度が高い*4のはWathanの式である。

#1-RMの重量を予測する式。repsは持ち上げた回数。repwtは持ち上げた重量。
wathan <- function(reps, repwt) {
  100 * repwt / (48.8 + 53.8 * exp(-0.075 * reps))
}

この式を使って記録を1-RMに変換すれば、異時点間の記録を比較することができそうだ。
早速使ってみた。

> po <- read.csv("pullover.csv")
> po$Date <- as.Date(po$Date)
> (po$oneRM <- wathan(po$Rep, po$Weight))
 [1] 44.65079 43.31901 48.50881 52.34528 52.34528 58.01330 55.35207
 [8] 58.01330 55.24615 58.01330 59.34035 59.34035 53.81099 59.34035
[15] 63.55606 67.37335 63.83571 65.62316 67.37335 69.08268 63.83571
[22] 67.37335 65.62316 69.08268 72.36628 72.18547 74.11068 75.99095
[29] 75.99095 77.82272 75.32614 77.43533 77.43533 77.43533 77.43533
[36] 74.11068 79.50055 81.51756

1-RMに変換された記録をプロットするとこんなグラフになった。

require(ggplot2)
g <- ggplot(po, aes(x = Date, y = oneRM))
g + geom_point()

f:id:stockedge:20160313223911p:plain
記録が直線的に伸びていることが確認できる。

トレンドのある時系列データをARIMA過程でモデル化する

せっかくだから、この記録データが今後どうなるかを予測してみた。
グラフを見れば明らかなように、これはトレンドのある時系列データ(つまり定常過程ではない)ので、ARIMAのような非定常過程のモデルを使う必要がある。*5
とはいっても、今回のデータには外れ値や季節変動は無いので、やるのはforecastパッケージのauto.arimaにデータを突っ込むだけの簡単なお仕事である。

> require(forecast)
> (oneRM.arima <- auto.arima(po$oneRM))
Series: po$oneRM 
ARIMA(0,1,1) with drift         

Coefficients:
          ma1   drift
      -0.4408  0.9705
s.e.   0.1927  0.2600

sigma^2 estimated as 7.571:  log likelihood=-87.13
AIC=180.26   AICc=180.99   BIC=185.1

ARIMA(0,1,1)が出力されたので、時系列の差分がMA(1)過程に従うモデルがAIC最小となるようだ。
追記:一応、残差の自己相関とシャピロ–ウィルク検定の結果も載せときます。

> acf(resid(oneRM.arima),plot=F)

Autocorrelations of series ‘resid(oneRM.arima), by lag

     0      1      2      3      4      5      6      7      8      9 
 1.000  0.037 -0.023 -0.177  0.089 -0.064 -0.218 -0.337  0.129 -0.046 
    10     11     12     13     14     15 
 0.220  0.042  0.154  0.080  0.052 -0.102 
> shapiro.test(resid(oneRM.arima))

	Shapiro-Wilk normality test

data:  resid(oneRM.arima)
W = 0.9741, p-value = 0.5121

では、このモデルを使って一カ月先の1-RMの重量を予測してみよう。私は週に1回程度の頻度で筋トレを行っているので、4期先を予測すればよい。

> forecast(oneRM.arima, h=4)
   Point Forecast    Lo 80    Hi 80    Lo 95    Hi 95
39       81.59668 78.07047 85.12290 76.20380 86.98956
40       82.56720 78.52710 86.60729 76.38840 88.74599
41       83.53771 79.04209 88.03333 76.66226 90.41316
42       84.50822 79.59917 89.41727 77.00048 92.01596
> plot(forecast(oneRM.arima, h=4))

f:id:stockedge:20160316095024p:plain
一ヶ月後、1-RMは約3kg増えるようだ。

さらに先へ

最後に、このモデルを使ってもっと先の値を予測してみた。

> tail(forecast(oneRM.arima, h=21000000)$mean,1)
[1] 20380850

2100万期先(=約40万年後)には2万トン*6を持ち上げることができるようだ。
ちなみに、ゴジラの体重も2万トンである。
いつかはゴジラも倒せると思えば筋トレのモチベーションも上がる、かも!?*7

*1:ちなみに筋トレは毎日やる必要は無く週に2回やるだけでよい。参考:http://yuchrszk.blogspot.jp/2015/05/2.html

*2:プルオーバー以外にも5種目ほどやっているが、PCへの数値入力が面倒だったので今回はプルオーバーの記録だけを扱うことにした

*3:私は8~12-RMの重量で約一分間のインターバルを置いて3セット行っている。この記録には1セット目の数値だけが書かれている

*4:あくまでもこの論文が行った三つの実験においては、だけど

*5:筋トレは2-3年目あたりから伸び悩むらしい(参考: http://blog.itokoji.com/archives/515059.html)ので、本当はレジームスイッチングモデルとかでモデル化したほうがいいかもしれないんだけど、データがないので、今回はARIMAでモデル化できるものと仮定して話を進める

*6:確率的トレンドの分散は時間とともに増大するのでこの予測値はあまり信用できる数値ではないんだけど

*7:もちろんこれを実現させるには、まずは不老不死の体にならないといけないのだが…