我似乎无法想出这个。我试图获得过去20天的列标准偏差。这就是我所拥有的
Model.where('date < ?','2013-03-25')
.group('date')
.order('date DESC')
.limit(20)
.select('stddev_samp(percent_change) as stdev')
然而,我得到的只有20个Nil条目。我期待标准差的一次输入。
将stddev_samp切换为sum之后,我发现因为你不能在1个条目上产生标准偏差,所以我得到了nil。即它没有像我预期的那样对20进行分组,而是在每个日期计算标准偏差。
所以我的问题是,如何获得过去20天的stddev?我知道可以简单地选择select percent_change
然后计算ruby中的标准差,但我假设在这种情况下聚合函数stddev_samp应该可用。
我正在使用rails 3.2和Postgresql 9.2
答案 0 :(得分:1)
我不是Ruby人,所以我会在普通的SQL中解释它:
您正在做的是:
SELECT stddev_samp(percent_change) as stdev
FROM tbl
WHERE date < '2013-03-25'
GROUP BY date
ORDER BY date DESC
LIMIT 20;
这会分别计算每一天的偏差,而不是它们的总和,当你试图得到只有一个元素的偏差时,你会得到NULL
。
删除GROUP BY
会修复它,但也会返回整个表的结果,而不仅仅是最后20个条目,所以我们需要一个子查询:
SELECT stddev_samp(percent_change) as stdev
FROM
(SELECT percent_change
FROM tbl
WHERE date < '2013-03-25'
ORDER BY date DESC
LIMIT 20) AS q
答案 1 :(得分:1)
无需'分组依据','排序依据'或子选择。只需获取过去20天的记录并在其上运行聚合函数。
红宝石:
Model.where('date >= ?', Date.today - 20.days).select('stddev_samp(percent_change) as stdev').first['stdev']
SQL:
select stddev_samp(percent_change) as stdev
from <table>
where date >= now() - interval 20 day;
如果您想使用最后20个记录,而不是过去20天:
红宝石:
Model.order('date desc').limit(20).select('stddev_samp(percent_change) as stdev').first['stdev']
SQL:
select stddev_samp(percent_change) as stdev
from <table>
order by date desc
limit 20;
答案 2 :(得分:0)
您不需要该组,因为您不希望每个日期都有一个值。
如果您有多个日期值或缺少日期
,您的限制也可能无效试试这个:
SELECT stddev_samp(percent_change) as stdev
FROM
(SELECT percent_change
FROM tbl
WHERE date > now() - interval '20 days') AS q