চলমান গড় গণনা করা হচ্ছে


185

আমি ম্যাট্রিক্সের মানগুলির সিরিজ ধরে চলমান গড় গণনা করতে আর ব্যবহার করার চেষ্টা করছি। সাধারণ আর মেলিং তালিকার সন্ধানটি তেমন সহায়ক হয়নি। আর -তে কোনও অন্তর্নির্মিত ফাংশন মনে হচ্ছে না যে আমাকে চলমান গড় গণনা করতে দেয়। কোন প্যাকেজ কি একটি সরবরাহ করে? নাকি আমার নিজের লেখার দরকার আছে?

উত্তর:


140

1
প্রদত্ত টাইমস্ট্যাম্পের ভবিষ্যতের মানগুলি না রাখে আরে মুভিং এভারেজটি কী? আমি চেক করেছি forecast::maএবং এটিতে সমস্ত পাড়া রয়েছে, ঠিক নয় not
এইচ এইচ

213

অথবা আপনি কেবল ফিল্টার ব্যবহার করে এটি গণনা করতে পারেন, এখানে আমি যে ফাংশনটি ব্যবহার করি তা এখানে:

ma <- function(x, n = 5){filter(x, rep(1 / n, n), sides = 2)}

আপনি যদি ব্যবহার করেন তবে উপরের dplyrফাংশনটিতে নির্দিষ্ট করতে সাবধান হন stats::filter


49
আমার উল্লেখ করা উচিত যে "পক্ষগুলি = 2" অনেক লোকের ব্যবহারের ক্ষেত্রে তারা অগ্রাহ্য করতে চান না এমন একটি গুরুত্বপূর্ণ বিকল্প হতে পারে। আপনি যদি আপনার চলমান গড়তে কেবল পিছনের তথ্য চান তবে আপনার পক্ষগুলি = 1 ব্যবহার করা উচিত।
খ্রিস্টান

35
কয়েক বছর পরে তবে ডিপিপ্লায়ার এখন একটি ফিল্টার ফাংশন রয়েছে, যদি আপনার এই প্যাকেজটি লোডযুক্ত ব্যবহার হয়stats::filter
blmoore

sides = 2চিড়িয়াখানা :: রোলমিন বা আরসিপিআরল :: রোল_মিনের জন্য প্রান্তিককরণ = "কেন্দ্র" এর সমান। sides = 1"ডান" সারিবদ্ধকরণের সমতুল্য। আমি "বাম" প্রান্তিককরণ করার কোনও উপায় দেখতে পাচ্ছি না বা "আংশিক" ডেটা (2 বা আরও বেশি মান) দিয়ে গণনা করব?
ম্যাট এল।

29

ব্যবহার cumsumযথেষ্ট এবং দক্ষ হতে হবে। ধরে নিচ্ছি আপনার কাছে ভেক্টর এক্স রয়েছে এবং আপনি n সংখ্যার একটি চলমান যোগ চান

cx <- c(0,cumsum(x))
rsum <- (cx[(n+1):length(cx)] - cx[1:(length(cx) - n)]) / n

@ এমজুথারের মন্তব্যে যেমন উল্লেখ করা হয়েছে, এটি ধরে নেওয়া হয়েছে যে ডেটাগুলিতে কোনও এনএ নেই। এগুলি মোকাবেলা করার জন্য প্রতিটি উইন্ডোকে নন-এনএ মানগুলির সংখ্যার দ্বারা ভাগ করা প্রয়োজন। @ রিকার্ডো ক্রুজের মন্তব্যটি সংযুক্ত করে এটি করার এক উপায় এখানে:

cx <- c(0, cumsum(ifelse(is.na(x), 0, x)))
cn <- c(0, cumsum(ifelse(is.na(x), 0, 1)))
rx <- cx[(n+1):length(cx)] - cx[1:(length(cx) - n)]
rn <- cn[(n+1):length(cx)] - cn[1:(length(cx) - n)]
rsum <- rx / rn

এটি এখনও সমস্যা আছে যে উইন্ডোতে সমস্ত মান যদি এনএ হয় তবে শূন্য ত্রুটির দ্বারা একটি বিভাগ থাকবে।


8
এই সমাধানের একটি নেতিবাচক cumsum(c(1:3,NA,1:3))
দিকটি হ'ল এটি মিসিংগুলি

আপনি এটি করে সহজেই এনএগুলি পরিচালনা করতে পারবেন cx <- c(0, cumsum(ifelse(is.na(x), 0, x)))
রিকার্ডো ক্রুজ

@ রিকার্ডো ক্রুজ: এনএগুলি অপসারণ এবং সেই অনুযায়ী ভেক্টরের দৈর্ঘ্য সামঞ্জস্য করা আরও ভাল। প্রচুর এনএ সহ ভেক্টরের কথা চিন্তা করুন - শূন্যগুলি গড়কে শূন্যের দিকে টানবে, যখন এনএগুলি সরানো গড় হিসাবে ছেড়ে যাবে। এটি অবশ্যই আপনার ডেটা এবং যে প্রশ্নের আপনি উত্তর দিতে চান তার উপর অবশ্যই নির্ভর করে। :)
mzuther

@ এমজুথার, আপনার মন্তব্যের পরে আমি উত্তর আপডেট করেছি। ইনপুট জন্য ধন্যবাদ। আমি মনে করি নিখোঁজ ডেটা নিয়ে কাজ করার সঠিক উপায়টি উইন্ডোটি প্রসারিত করছে না (এনএ মানগুলি সরিয়ে দিয়ে), তবে প্রতিটি উইন্ডোকে সঠিক ডিনোমিনেটর দ্বারা গড় হিসাবে গড়ে তোলা হচ্ছে।
পাইপফিশ

1
rn <- cn [(n + 1): দৈর্ঘ্য (cx)] - cx [1: (দৈর্ঘ্য (cx) - n)] আসলে rn <- cn [(n + 1): দৈর্ঘ্য (cx)] হওয়া উচিত - সিএন [1: (দৈর্ঘ্য (সিএক্স) - এন)]
অ্যাড্রিয়ানমেকেনামিন

22

ইন data.table 1.12.0 নতুন frollmeanফাংশন দ্রুত এবং সঠিক সাবধানে গড় ঘূর্ণায়মান হ্যান্ডলিং গনা যোগ করা হয়েছে NA, NaNএবং +Inf, -Infমান।

যেহেতু প্রশ্নের কোনও পুনরুত্পাদনযোগ্য উদাহরণ নেই এখানে এখানে সম্বোধনের মতো বেশি কিছু নেই।

আপনি ?frollmeanম্যানুয়াল সম্পর্কে আরও তথ্য সন্ধান করতে পারেন , অনলাইনেও উপলভ্য ?frollmean

নীচে ম্যানুয়াল থেকে উদাহরণ:

library(data.table)
d = as.data.table(list(1:6/2, 3:8/4))

# rollmean of single vector and single window
frollmean(d[, V1], 3)

# multiple columns at once
frollmean(d, 3)

# multiple windows at once
frollmean(d[, .(V1)], c(3, 4))

# multiple columns and multiple windows at once
frollmean(d, c(3, 4))

## three above are embarrassingly parallel using openmp

10

caToolsপ্যাকেজ খুব দ্রুত গড় / মিনিট / সর্বোচ্চ / এসডি এবং কয়েক অন্যান্য ফাংশন ঘূর্ণায়মান হয়েছে। আমি শুধু সঙ্গে কাজ করেছি runmeanএবং runsdতারা অন্যান্য প্যাকেজ তারিখ থেকে উল্লিখিত কোনো দ্রুততম হয়।


1
এটা সত্যিই দারুন! এটি একমাত্র ফাংশন যা এটি একটি সুন্দর, সরল উপায়ে করে। এবং এটি এখন 2018 ...
ফিলিপ জেরার্ড

9

আপনি RcppRollসি ++ তে লিখিত খুব দ্রুত চলমান গড়ের জন্য ব্যবহার করতে পারেন । শুধু roll_meanফাংশন কল । দস্তাবেজগুলি এখানে পাওয়া যাবে

অন্যথায়, লুপের জন্য এই (ধীর) কৌশলটি করা উচিত:

ma <- function(arr, n=15){
  res = arr
  for(i in n:length(arr)){
    res[i] = mean(arr[(i-n):i])
  }
  res
}

3
আপনি দয়া করে আমাকে বিশদে ব্যাখ্যা করতে পারেন, এই অ্যালগরিদম কীভাবে কাজ করে? কারণ আমি ধারণাটি বুঝতে পারি না
ড্যানিয়েল ইয়েফিমভ

প্রথমে তিনি একই দৈর্ঘ্যের একটি ভেক্টর সূচনা করেন res = arr। তারপরে একটি লুপ রয়েছে যা n15 ম এলিমেন্টটি অ্যারের শেষ পর্যন্ত শুরু হয় বা পুনরাবৃত্তি করে। তার অর্থ তিনি যে প্রথম উপসেটটি গ্রহণ করেন তা হ'ল arr[1:15]যা স্পট পূরণ করে res[15]। এখন, আমি এর res = rep(NA, length(arr))পরিবর্তে সেট করতে পছন্দ করি res = arrপ্রতিটি res[1:14]সংখ্যার চেয়ে NA এর সমান, যেখানে আমরা 15 টি উপাদানের পুরো গড় নিতে পারি না।
ইভান ফ্রিডল্যান্ড

7

আসলে RcppRollখুব ভাল।

ক্যানডাথাথগুলি পোস্ট করা কোডটি অবশ্যই চতুর্থ লাইনে উইন্ডোতে সংশোধন করতে হবে:

ma <- function(arr, n=15){
  res = arr
  for(i in n:length(arr)){
    res[i] = mean(arr[(i-n+1):i])
  }
  res
}

আর একটি উপায়, যা মিসিংগুলি পরিচালনা করে, এখানে দেওয়া আছে

তৃতীয় উপায়, আংশিক গড় বা না গণনা করার জন্য ক্যান্টচিটস কোডটি উন্নত করা হচ্ছে :

  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,...)]
  }
}

5

ক্যানডাচথিস এবং রডরিগো রেমিডির উত্তর পরিপূরক করতে ;

moving_fun <- function(x, w, FUN, ...) {
  # x: a double vector
  # w: the length of the window, i.e., the section of the vector selected to apply FUN
  # FUN: a function that takes a vector and return a summarize value, e.g., mean, sum, etc.
  # Given a double type vector apply a FUN over a moving window from left to the right, 
  #    when a window boundary is not a legal section, i.e. lower_bound and i (upper bound) 
  #    are not contained in the length of the vector, return a NA_real_
  if (w < 1) {
    stop("The length of the window 'w' must be greater than 0")
  }
  output <- x
  for (i in 1:length(x)) {
     # plus 1 because the index is inclusive with the upper_bound 'i'
    lower_bound <- i - w + 1
    if (lower_bound < 1) {
      output[i] <- NA_real_
    } else {
      output[i] <- FUN(x[lower_bound:i, ...])
    }
  }
  output
}

# example
v <- seq(1:10)

# compute a MA(2)
moving_fun(v, 2, mean)

# compute moving sum of two periods
moving_fun(v, 2, sum)

2

এখানে কিভাবে গনা একটি দেখাচ্ছে উদাহরণ কোড কেন্দ্রিক গড় চলন্ত এবং একটি trailing গড় চলন্ত ব্যবহার rollmeanথেকে ফাংশন চিড়িয়াখানা প্যাকেজ।

library(tidyverse)
library(zoo)

some_data = tibble(day = 1:10)
# cma = centered moving average
# tma = trailing moving average
some_data = some_data %>%
    mutate(cma = rollmean(day, k = 3, fill = NA)) %>%
    mutate(tma = rollmean(day, k = 3, fill = NA, align = "right"))
some_data
#> # A tibble: 10 x 3
#>      day   cma   tma
#>    <int> <dbl> <dbl>
#>  1     1    NA    NA
#>  2     2     2    NA
#>  3     3     3     2
#>  4     4     4     3
#>  5     5     5     4
#>  6     6     6     5
#>  7     7     7     6
#>  8     8     8     7
#>  9     9     9     8
#> 10    10    NA     9

1

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নির্দিষ্ট সূচকগুলি রোল করতে পারে । আরো প্যাকেজ এবং ফাংশন ডকুমেন্টেশন।


0

যদিও কিছুটা ধীর হলেও আপনি ম্যাট্রিকেসে গণনা করতে চিড়িয়াখানা :: রোলপ্লাই ব্যবহার করতে পারেন।

reqd_ma <- rollapply(x, FUN = mean, width = n)

যেখানে এক্স ডেটা সেট করা হয়, FUN = গড়টি হল ফাংশন; আপনি এটিকে নূন্যতম, সর্বোচ্চ, এসডি ইত্যাদিতেও পরিবর্তন করতে পারেন এবং প্রস্থটি রোলিং উইন্ডো।


1
এটা ধীর নয়;। এটি বেস আর এর সাথে তুলনা করে, এটি অনেক দ্রুত। set.seed(123); x <- rnorm(1000); system.time(apply(embed(x, 5), 1, mean)); library(zoo); system.time(rollapply(x, 5, mean)) আমার মেশিনে এটি এত দ্রুত যে এটি 0 সেকেন্ডের সময় ফিরে আসে।
জি গ্রোথেনডিক

0

স্লাইডার প্যাকেজটির জন্য এটি ব্যবহার করা যেতে পারে। এটির একটি ইন্টারফেস রয়েছে যা বিশেষত purrr এর সাথে অনুরূপ বোধ করার জন্য ডিজাইন করা হয়েছে। এটি যেকোন স্বেচ্ছাসেবী ফাংশন গ্রহণ করে এবং যে কোনও ধরণের আউটপুট ফেরত দিতে পারে। ডেটা ফ্রেমগুলি সারিবদ্ধভাবে পুনরাবৃত্তি হয়। পিকেডাউন সাইটটি এখানে

library(slider)

x <- 1:3

# Mean of the current value + 1 value before it
# returned as a double vector
slide_dbl(x, ~mean(.x, na.rm = TRUE), .before = 1)
#> [1] 1.0 1.5 2.5


df <- data.frame(x = x, y = x)

# Slide row wise over data frames
slide(df, ~.x, .before = 1)
#> [[1]]
#>   x y
#> 1 1 1
#> 
#> [[2]]
#>   x y
#> 1 1 1
#> 2 2 2
#> 
#> [[3]]
#>   x y
#> 1 2 2
#> 2 3 3

স্লাইডার এবং ডেটা উভয়েরই ওভারহেড frollapply()খুব কম হওয়া উচিত (চিড়িয়াখানার থেকে অনেক দ্রুত) much frollapply()এখানে এই সাধারণ উদাহরণটির জন্য কিছুটা দ্রুত হতে দেখায়, তবে মনে রাখবেন যে এটি কেবল সংখ্যার ইনপুট নেয় এবং আউটপুটটি অবশ্যই একটি স্কেলারের সংখ্যাসূচক মান হওয়া উচিত। স্লাইডার ফাংশনগুলি সম্পূর্ণ জেনেরিক এবং আপনি কোনও ডেটা টাইপ ফিরতে পারেন।

library(slider)
library(zoo)
library(data.table)

x <- 1:50000 + 0L

bench::mark(
  slider = slide_int(x, function(x) 1L, .before = 5, .complete = TRUE),
  zoo = rollapplyr(x, FUN = function(x) 1L, width = 6, fill = NA),
  datatable = frollapply(x, n = 6, FUN = function(x) 1L),
  iterations = 200
)
#> # A tibble: 3 x 6
#>   expression      min   median `itr/sec` mem_alloc `gc/sec`
#>   <bch:expr> <bch:tm> <bch:tm>     <dbl> <bch:byt>    <dbl>
#> 1 slider      19.82ms   26.4ms     38.4    829.8KB     19.0
#> 2 zoo        177.92ms  211.1ms      4.71    17.9MB     24.8
#> 3 datatable    7.78ms   10.9ms     87.9    807.1KB     38.7
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.