2016-12-05 228 views
0

給定一個像下面這樣的Hive表,我想計算加權移動平均數。表1是這種加權移動平均數的一個例子。每列的值是在加權移動平均加權移動平均值與Hive SQL

col_value = (1 * n) + (0.75 * n-1) + (0.5 * n-2) + (0.25 * n-3) 
where n is the value at the current row, n-1 the value at the above row, etc. 

更多信息在corresponding Wikipedia section

林計算移動平均,像這樣後卡住:到目前爲止

查詢:

代碼示例1

SELECT *, AVG (value) OVER ( ORDER BY id ROWS BETWEEN 3 PRECEDING AND CURRENT ROW FROM table 

表1:

id value weighted_moving_average code_sample_1 
... 
11  0  0      0 
12  1  1      0.25 
13  0  0.75      0.25 
14  0  0.5      0.25 
15  0  0.25      0.25 
16  0  0      0 
... 
+1

你能解釋'wanted'列的邏輯嗎? –

+0

你從運行該查詢得到什麼? –

+0

感謝您的建議,請參閱更新的問題 –

回答

1

如果你想在窗口大小可以很容易地改變,那麼實現將是顯着不同。

(請注意,我開發了這個在,因爲我不知道任何網站,我可以測試 SQL的。你可能需要調整一些語法)。

Declare @thisManyRows int = 3; 
With rowNumber_cte As (
    Select 
     id, 
     [Value], 
     RowNo = Row_Number() Over (Order By id) 
     From Table1), 
windows_cte As (
    Select 
     b_id = b.id, 
     j_id = j.id, 
     j.[Value], 
     RowNo2 = @thisManyRows + 1 - Row_Number() Over (Partition By b.id Order By j.id desc), 
     n = Count(j.[Value]) Over (Partition By b.id) 
     From rowNumber_cte As b 
     Join rowNumber_cte As j On j.RowNo Between b.RowNo - @thisManyRows + 1 And b.RowNo) 
Select 
    id = b_id, 
    [Value] = Sum(Case When b_id = j_id Then [Value] Else Null End), 
    WeightedAverage = Sum([Value] * 1.0 * (RowNo2 *1.0/@thisManyRows))/Min(n) 
    From windows_cte 
    Group By b_id; 

我要解釋什麼這是因爲它有點神祕:

  1. 將變量設置爲移動平均值(包括當前行)考慮的行數。
  2. rowNumber_cte我們分配一個行號,我們這樣做是因爲我們不假定id將是連續的。
  3. windows_cte我們本身加入rowNumber_cte,使每一行被加入到構成它的計算(窗口參考@thisManyRows變量的所有行。這CTE還引入了新RowNo2場將基本結束向上是作爲該行的值有助於加權移動平均的分數的分子(即,當前行,如果窗口是4將具有RowNo2 = 4並且將具有4/4的重量)。
  4. windows_cte還計算的數窗口中的行可以更好地處理沒有完整窗口的數據開始處的行。
  5. 最終選擇組由id,將窗口中每行的[Value]乘以其權重,然後除以窗口中的行數:n
0

這不是花哨的,但它是一個開始。

SELECT 
    *, 
    (SUM (value*0.25) OVER (ORDER BY id ROWS BETWEEN 3 PRECEDING AND CURRENT ROW) + 
    SUM (value*0.25) OVER (ORDER BY id ROWS BETWEEN 2 PRECEDING AND CURRENT ROW) + 
    SUM (value*0.25) OVER (ORDER BY id ROWS BETWEEN 1 PRECEDING AND CURRENT ROW) + 
    value * 0.25)/
    COUNT (value) OVER (ORDER BY id ROWS BETWEEN 3 PRECEDING AND CURRENT ROW) 
FROM 
    table; 
+0

任何使窗口大小動態的方法? –

+0

不在他的方法。我可以想出一個不同的方式來做到這一點,但這可能是動態的,但我現在沒有時間寫。 – mendosi