Rを使用して、マトリックス内の一連の値の移動平均を計算しようとしています。Rには、移動平均を計算できる組み込み関数がないようです。パッケージはそれを提供しますか?それとも私は自分で書く必要がありますか?
17 に答える
または、フィルターを使用して単純に計算することもできます。私が使用する関数は次のとおりです。
ma <- function(x, n = 5){filter(x, rep(1 / n, n), sides = 2)}
を使用する場合は、上記の関数でのdplyr
指定に注意してください。stats::filter
このcaTools
パッケージには、平均値/最小値/最大値/標準偏差のローリングが非常に高速で、その他の機能はほとんどありません。私はrunmean
andのみを使用しましrunsd
たが、これまでに言及された他のパッケージの中で最も高速です。
RcppRoll
C++ で書かれた非常に高速な移動平均に使用できます。関数を呼び出すだけroll_mean
です。ドキュメントはここにあります。
それ以外の場合は、この (遅い) for ループでうまくいくはずです:
ma <- function(arr, n=15){
res = arr
for(i in n:length(arr)){
res[i] = mean(arr[(i-n):i])
}
res
}
実際RcppRoll
、とても良いです。
cantdutchthisによって投稿されたコードは、ウィンドウを修正するために 4 行目を修正する必要があります。
ma <- function(arr, n=15){
res = arr
for(i in n:length(arr)){
res[i] = mean(arr[(i-n+1):i])
}
res
}
欠落を処理する別の方法をここに示します。
部分平均を計算するかどうかを計算するためにcantdutchthisコードを改善する 3 番目の方法は次のとおりです。
ma <- function(x, n=2,parcial=TRUE){
res = x #set the first values
if (parcial==TRUE){
for(i in 1:length(x)){
t<-max(i-n+1,1)
res[i] = mean(x[t:i])
}
res
}else{
for(i in 1:length(x)){
t<-max(i-n+1,1)
res[i] = mean(x[t:i])
}
res[-c(seq(1,n-1,1))] #remove the n-1 first,i.e., res[c(-3,-4,...)]
}
}
x
ウィンドウ幅のベクトルの移動平均は、次の方法で計算できますk
。
apply(embed(x, k), 1, mean)
EDIT :ベクトルside
の過去 7 日間の移動平均 (または合計など)のパラメーターを追加することに大きな喜びを感じました。Date
これを自分で計算したいだけの人にとっては、次のとおりです。
# x = vector with numeric data
# w = window length
y <- numeric(length = length(x))
for (i in seq_len(length(x))) {
ind <- c((i - floor(w / 2)):(i + floor(w / 2)))
ind <- ind[ind %in% seq_len(length(x))]
y[i] <- mean(x[ind])
}
y
しかし、 から独立させると楽しくなるmean()
ので、任意の「動く」関数を計算できます!
# our working horse:
moving_fn <- function(x, w, fun, ...) {
# x = vector with numeric data
# w = window length
# fun = function to apply
# side = side to take, (c)entre, (l)eft or (r)ight
# ... = parameters passed on to 'fun'
y <- numeric(length(x))
for (i in seq_len(length(x))) {
if (side %in% c("c", "centre", "center")) {
ind <- c((i - floor(w / 2)):(i + floor(w / 2)))
} else if (side %in% c("l", "left")) {
ind <- c((i - floor(w) + 1):i)
} else if (side %in% c("r", "right")) {
ind <- c(i:(i + floor(w) - 1))
} else {
stop("'side' must be one of 'centre', 'left', 'right'", call. = FALSE)
}
ind <- ind[ind %in% seq_len(length(x))]
y[i] <- fun(x[ind], ...)
}
y
}
# and now any variation you can think of!
moving_average <- function(x, w = 5, side = "centre", na.rm = FALSE) {
moving_fn(x = x, w = w, fun = mean, side = side, na.rm = na.rm)
}
moving_sum <- function(x, w = 5, side = "centre", na.rm = FALSE) {
moving_fn(x = x, w = w, fun = sum, side = side, na.rm = na.rm)
}
moving_maximum <- function(x, w = 5, side = "centre", na.rm = FALSE) {
moving_fn(x = x, w = w, fun = max, side = side, na.rm = na.rm)
}
moving_median <- function(x, w = 5, side = "centre", na.rm = FALSE) {
moving_fn(x = x, w = w, fun = median, side = side, na.rm = na.rm)
}
moving_Q1 <- function(x, w = 5, side = "centre", na.rm = FALSE) {
moving_fn(x = x, w = w, fun = quantile, side = side, na.rm = na.rm, 0.25)
}
moving_Q3 <- function(x, w = 5, side = "centre", na.rm = FALSE) {
moving_fn(x = x, w = w, fun = quantile, side = side, na.rm = na.rm, 0.75)
}
runner
関数を移動するためにパッケージを使用できます。この場合、mean_run
機能します。問題は、値をcummean
処理しないことですが、処理します。パッケージは不規則な時系列もサポートしており、ウィンドウは日付に依存する可能性があります:NA
mean_run
runner
library(runner)
set.seed(11)
x1 <- rnorm(15)
x2 <- sample(c(rep(NA,5), rnorm(15)), 15, replace = TRUE)
date <- Sys.Date() + cumsum(sample(1:3, 15, replace = TRUE))
mean_run(x1)
#> [1] -0.5910311 -0.2822184 -0.6936633 -0.8609108 -0.4530308 -0.5332176
#> [7] -0.2679571 -0.1563477 -0.1440561 -0.2300625 -0.2844599 -0.2897842
#> [13] -0.3858234 -0.3765192 -0.4280809
mean_run(x2, na_rm = TRUE)
#> [1] -0.18760011 -0.09022066 -0.06543317 0.03906450 -0.12188853 -0.13873536
#> [7] -0.13873536 -0.14571604 -0.12596067 -0.11116961 -0.09881996 -0.08871569
#> [13] -0.05194292 -0.04699909 -0.05704202
mean_run(x2, na_rm = FALSE )
#> [1] -0.18760011 -0.09022066 -0.06543317 0.03906450 -0.12188853 -0.13873536
#> [7] NA NA NA NA NA NA
#> [13] NA NA NA
mean_run(x2, na_rm = TRUE, k = 4)
#> [1] -0.18760011 -0.09022066 -0.06543317 0.03906450 -0.10546063 -0.16299272
#> [7] -0.21203756 -0.39209010 -0.13274756 -0.05603811 -0.03894684 0.01103493
#> [13] 0.09609256 0.09738460 0.04740283
mean_run(x2, na_rm = TRUE, k = 4, idx = date)
#> [1] -0.187600111 -0.090220655 -0.004349696 0.168349653 -0.206571573 -0.494335093
#> [7] -0.222969541 -0.187600111 -0.087636571 0.009742884 0.009742884 0.012326968
#> [13] 0.182442234 0.125737145 0.059094786
などの他のオプションを指定して、特定のインデックスlag
のみをロールすることもできます。パッケージと関数のドキュメントat
の詳細。