【问题标题】:Moving averages with crossfilter.js and dc.js使用 crossfilter.js 和 dc.js 移动平均线
【发布时间】:2013-12-15 15:01:17
【问题描述】:

我想将 crossfilter.js 与 dc.js 一起使用以表示移动平均线。

是否可以计算一组数据的移动平均值,或者如果传入的数据必须已经计算了平均值?

如果可以的话,请你提供一个简短的例子。

谢谢,

【问题讨论】:

  • 我不太确定你的目标是什么。据我所知,使用这些库应该是完全可能的,因为在某一时刻你必须将数据推送到它们中,所以只需计算 n 个元素的平均值并推送它而不是推送元素本身。您将在实时方面落后大约 n/2 个元素。在我看来,只要你能画出正常数据,你就能画出移动平均线。

标签: crossfilter dc.js


【解决方案1】:

我很想被证明是错误的,但我真的想不出在 crossfilter 中这样做的方法。

在时间序列的情况下,reduce() 函数将用于跨数据执行聚合,按日期分组,如下面突出显示的单元格:

使用移动平均线,您需要通过向下循环行来执行操作:

在服务器端,我不会选择 SQL 来计算数据库数据的移动平均值;同样,我不会使用 crossfilter 客户端。

【讨论】:

    【解决方案2】:

    我不知道你是否还在寻求任何帮助,但我自己刚刚克服了这个问题,我想我会分享我的解决方案,以防它帮助其他人。

    首先,我声明了一些非常标准的reduce 函数来返回一个简单的平均值,并添加了两个变量来存储 t-1 和 t-2 的平均值。我创建了一个 3 周期移动平均线,但如果您想要一个更长的移动平均线,您可以轻松地将这些变量替换为您 pushsplice 数据传入/传出的数组。

    function movingAveInit(){
      return {
        total: 0,
        count: 0,
        average: 0,
        //These are the two vars for storing previous periods
        avet1: 150000,
        avet2: 150000
      };
    }
    
    function movingAveAdd(p,v){
      //'apples' is the property that you're interested in finding the moving average for
      p.total = p.total + v.apples;
      p.count = p.count +1;
      p.avet2 = p.avet1;
      p.avet1 = p.average;
      p.average = p.total/p.count;
      return p;
    }
    
    function movingAveRemove(p,v){
      p.total = p.total - v.apples;
      p.count = p.count - 1;
      p.avet2 = p.avet1;
      p.avet1 = p.average;
      p.average = p.total/p.count;
      return p;
    }
    

    接下来在您的组中调用这些(维度应该是您使用的任何时间段):

    var movingAverageGrp = yourDimension.group().reduce(movingAveAdd, movingAveRemove, movingAveInit);
    

    现在,当您使用该组构建图表时,将以下内容添加到其valueAccessor()

    yourChart
      .valueAccessor(function (d) { 
    
            var mAv = ((d.value.avet2 + d.value.avet1 + d.value.average) / 3);
            return mAv; 
       })
    

    如果您将以前的周期存储在一个数组中,则可以使用此函数来计算移动平均线:

    .valueAccessor(function (d) { 
    
        var sum = d.value.yourArray.reduce(function(a, b){ return a + b; });
        var count = d.value.yourArray.length;        
        var mAv = (sum / count);
        return mAv;
    
        })
    

    这不是一个特别漂亮的解决方案,但它似乎对我有用。

    【讨论】:

      猜你喜欢
      • 2017-09-01
      • 2022-01-26
      • 2013-12-22
      • 1970-01-01
      • 2016-11-27
      • 1970-01-01
      • 2021-07-11
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多