改善data.table中滚动平均值的使用

时间:2018-12-09 08:05:19

标签: r data.table

我正在尝试将一个函数复制在一起

library(tidyverse)
library(magrittr)
library(data.table)
library(parallel)
library(RcppRoll)

windows <- (1:10)*600

df2 <- setDT(df_1, key=c("Match","Name"))[
  ,by=.(Match, Name), paste0("Period_", 1:10)
  := mclapply((1:10)*600, function(x) roll_mean(Dist, x))][]

它基于分配给windows的值创建滚动平均值 我有一个可以复制它的工作函数,但是我觉得有一种更好的方法,因为函数版本处理数据的时间将近30倍

dt_rolling <- function(df, the.keys, x, y, z, window){
  df <- data.table(df)
  setkeyv(df, the.keys) 
  df[,by=.(x,y), paste0("Period_", window) := mclapply(window, function(a) roll_mean(z, a))][]
}


df2 <- dt_rolling(df_1, the.keys=c('Match', 'Name'), df_1$Match, df_1$Name, df_1$Dist, windows)

有问题的数据如下

> dput(head(df_1, 5))
structure(list(Match = c("BathH", "BathH", "BathH", "BathH", 
"BathH"), Name = c("Alafoti Faosiliva", "Alafoti Faosiliva", 
"Alafoti Faosiliva", "Alafoti Faosiliva", "Alafoti Faosiliva"
), Dist = c(0, 0, 0, 0, 0), Period_1 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_2 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_3 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_4 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_5 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_6 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_7 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_8 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_9 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_10 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_600 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_1200 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_1800 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_2400 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_3000 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_3600 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_4200 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_4800 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_5400 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_), Period_6000 = c(NA_real_, NA_real_, 
NA_real_, NA_real_, NA_real_)), sorted = c("Match", "Name"), class =     c("data.table", 
"data.frame"), row.names = c(NA, -5L), .internal.selfref = <pointer:   0x10280cae0>)

它可以扩展到超过2000万行,这就是为什么我在这里使用data.table方法以及调查将其更改为函数的原因

编辑:

下面@jangorecki关于添加data.table::frollmean()的答案之后,我在具有1,500,000行的数据集上使用frollmeanRcpp与基于microbenchmark的滚动平均值函数进行了比较。

Unit: seconds
       expr      min       lq     mean   median       uq      max neval cld
       rcpp 1.056967 1.224827 1.374116 1.304310 1.467108 5.855003  1000  a 
 data.table 1.096122 1.306993 1.466128 1.389878 1.549299 9.287606  1000   b

enter image description here

1 个答案:

答案 0 :(得分:5)

从v1.12.0版本开始,快速滚动平均值在data.table中可用。
以下查询将解决您的问题。

$(document).ready(function() {

      // Initialize air datepicker plugin
      $('.air-datepicker').datepicker();

      // Store form into variable
      var form= $("#requestForm");

      // Actions when form is submitted
      $('#submitForm').click(function(e) {

        // Ajax request
        $.ajax({

          type: "POST",
          data: form.serialize(),
          dataType:"html",

          success: function(result){

            // Reload the iframe with new content
            document.getElementById('tableContainer').contentDocument.location.reload(true);
            // Show the iframe
            $('#tableContainer').css('display','block');

            var $iframe = $('#tableContainer');

            $iframe.ready(function() {
                // append result to the iframe
                $iframe.contents().find("body").append(result);

            });


          },

          error: function(jqXHR, exception) {

            if (jqXHR.status === 0) {

              swal('Il server non risponde', 'Siamo spiacenti non è stato possibile eseguire questa operazione, per favore contatta l\'amministratore di sistema.', 'info');

            } else if (jqXHR.status == 404) {

              swal('Errore 404', 'Siamo spiacenti non è stato possibile eseguire questa operazione, per favore contatta l\'amministratore di sistema.', 'info');

            } else if (jqXHR.status == 500) {

              swal('Errore 500', 'Siamo spiacenti non è stato possibile eseguire questa operazione, per favore contatta l\'amministratore di sistema.', 'info');

            } else if (exception === 'parsererror') {

              swal('Si è verificato un errore!', 'Siamo spiacenti non è stato possibile eseguire questa operazione, per favore contatta l\'amministratore di sistema.', 'info');

            } else if (exception === 'timeout') {

              swal('Time Out', 'Siamo spiacenti non è stato possibile eseguire questa operazione, per favore contatta l\'amministratore di sistema.', 'info');

            } else if (exception === 'abort') {

              swal('Richiesta Annullata', 'Siamo spiacenti non è stato possibile eseguire questa operazione, per favore contatta l\'amministratore di sistema.', 'info');

            }


          }

        }); // Fine ajax


       e.preventDefault(); // Prevent form to be sent


      }); // fine submit form


    }); // fine document ready