R パッケージの caret は、相互検証で使用されるトレーニング セットのインデックスのリストを返す便利な関数createFoldsを提供します。
set.seed(1)
require(caret)
x <- rnorm(10)
createFolds(x,k=5,returnTrain=TRUE)
$Fold1
[1] 1 2 5 6 7 8 9 10
$Fold2
[1] 1 3 4 5 6 8 9 10
$Fold3
[1] 1 2 3 4 5 7 8 10
$Fold4
[1] 1 2 3 4 6 7 8 9
$Fold5
[1] 2 3 4 5 6 7 9 10
時系列の相互検証で使用されるインデックスのリストを返したいことを除いて、同様の関数を作成したいと思います。R でいくつかのサンプル コードを見つけましたが、もっと一般化して機能化したいと考えています。これが私が最初に思いついたものです:
createTSfolds <- function(y, Min=max(frequency(y),3)) {
i <- seq(along=y)
stops <- i[Min:(length(i)-1)]
starts <- rep(1,length(stops))
out <- mapply(seq,starts,stops)
names(out) <- paste("Fold", gsub(" ", "0", format(seq(along = out))), sep = "")
out
}
createTSfolds(x)
$Fold1
[1] 1 2 3
$Fold2
[1] 1 2 3 4
$Fold3
[1] 1 2 3 4 5
$Fold4
[1] 1 2 3 4 5 6
$Fold5
[1] 1 2 3 4 5 6 7
$Fold6
[1] 1 2 3 4 5 6 7 8
$Fold7
[1] 1 2 3 4 5 6 7 8 9
(最小は、モデルを適合させるために必要な観測の最小数です)
この関数は今のところうまく機能しますが、Rob Hyndman が議論している 2 つの関数を追加したいと思います。
- ウィンドウ処理: トレーニング セットを最初の観測に戻す代わりに、n 個の観測に戻します。
- 可変予測範囲: 各フォールドのトレーニング セットに 1 つのインデックスを追加する代わりに、各フォールドのトレーニング セットに k を追加します。
ウィンドウ処理を実装する方法は次のとおりです。
createTSfolds <- function(y, Min=max(frequency(y),3), lookback=NA) {
i <- seq(along=y)
stops <- i[Min:(length(i)-1)]
if (is.na(lookback)) {
starts <- as.list(rep(1,length(stops)))
out <- mapply(seq,starts,stops)
} else {
starts <- stops-Min+1
out <- mapply(seq,starts,stops)
out <- split(t(out),1:nrow(t(out)))
}
names(out) <- paste("Fold", gsub(" ", "0", format(seq(along = out))), sep = "")
out
}
createTSfolds(x,Min=4,lookback=4)
次のような可変予測範囲を実装する方法がわかりません: たとえば、k=3 の場合:
$Fold1
[1] 1 2 3
$Fold2
[1] 1 2 3 4 5 6
$Fold3
[1] 1 2 3 4 5 6 7 8 9
既存のコードを改善する方法と、フォールドごとにトレーニング セットに変数のインクリメントを追加する方法を探しています。
ありがとうございました