2017-08-07 138 views
0

我有這樣的表,只有兩列,每個記錄存儲在給定月份的利率:MySQL的計算查詢

id  rate 
=========== 
199502 3.63 
199503 2.60 
199504 4.26 
199505 4.25 
... ... 
201704 0.79 
201705 0.93 
201706 0.81 
201707 0.80 
201708 0.14 

在此基礎上的價格,我需要創造積累率,相似的結構的另一個表,其數據被計算爲YYYYMM(月/年)參數,這樣的函數(在該式是法律上強制性):

  1. 給定的參數月有總是速率的0(零)
  2. 的一個月之前有alwa ys率爲1(一)
  3. 前幾個月的費率將爲(一)加上給定月份與月份之間月份費率之和作爲參數。

我會澄清這個規則,這個例子中,給出的參數201708

SOURCE   CALCULATED 
id  rate id  rate 
=========== ============= 
199502 3.63 199502 360.97 (1 + sum(rate(199503) to rate(201707))) 
199503 2.60 199503 358.37 (1 + sum(rate(199504) to rate(201707))) 
199504 4.26 199504 354.11 (1 + sum(rate(199505) to rate(201707))) 
199505 4.25 199505 349.86 (1 + sum(rate(199506) to rate(201707))) 
... ...  ... ... 
201704 0.79 201704 3.54 (1 + rate(201705) + rate(201706) + rate(201707)) 
201705 0.93 201705 2.61 (1 + rate(201706) + rate(201707)) 
201706 0.81 201706 1.80 (1 + rate(201707)) 
201707 0.80 201707 1.00 (per definition) 
201708 0.14 201708 0.00 (per definition) 

現在我已經實現了一個VB.NET函數讀取源表並生成計算表,但

Public Function AccumRates(targetDate As Date) As DataTable 
    Dim dtTarget = Rates.Clone 
    Dim targetId = targetDate.ToString("yyyyMM") 
    Dim targetIdAnt = targetDate.AddMonths(-1).ToString("yyyyMM") 
    For Each dr In Rates.Select("id<=" & targetId & " and id>199412") 
     If dr("id") = targetId Then 
      dtTarget.Rows.Add(dr("id"), 0) 
     ElseIf dr("id") = targetIdAnt Then 
      dtTarget.Rows.Add(dr("id"), 1) 
     Else 
      Dim intermediates = 
       Rates.Select("id>" & dr("id") & " and id<" & targetId).Select(
        Function(ldr) New With { 
         .id = ldr.Field(Of Integer)("id"), 
         .rate = ldr.Field(Of Decimal)("rate")} 
        ).ToArray 
      dtTarget.Rows.Add(
       dr("id"), 
       1 + intermediates.Sum(
        Function(i) i.rate)) 
     End If 
    Next 
    Return dtTarget 
End Function 

我的問題是我怎麼可以把這個作爲我的數據庫查詢,因此它可以被其他動態查詢使用將使用這些積累率:這是在運行在每臺客戶機完成s更新債務到任何給定的日期。

非常感謝!

編輯

我設法讓返回我想要的數據的查詢,現在我只是不知道如何封裝,以便它可以從傳遞任何id作爲參數(另一查詢被稱爲在這裏我做到了使用SET ...聲明):

SET @targetId=201708; 
SELECT 
    id AS id_acum, 
    COALESCE(1 + (SELECT 
        SUM(taxa) 
       FROM 
        tableSelic AS ts 
       WHERE 
        id > id_acum AND id < @targetId 
       LIMIT 1), 
      IF(id >= @targetId, 0, 1)) AS acum 
FROM 
    tableSelic 
    WHERE id>199412; 

那是因爲我很新到MySQL,我已經習慣了MS-訪問,其中參數化查詢非常straightfoward創建。

+0

給定參數201708 ..爲什麼201706比例不是1.94? '1 + 0.80 + 0.14' –

+0

當前月份不完整,其匯率不計入累計匯率。法律的東西。 – VBobCat

+0

好的,那麼規則3應該寫成不同,以使其清楚不包含參數。 –

回答

0

好吧,我有一個功能使它:

CREATE FUNCTION `AccumulatedRates`(start_id integer, target_id integer) RETURNS decimal(6,2) 
BEGIN 
    DECLARE select_var decimal(6,2); 
    SET select_var = (
     SELECT COALESCE(1 + (
      SELECT SUM(rate) 
      FROM tableRates 
      WHERE id > start_id AND id < target_id LIMIT 1 
      ), IF(id >= unto, 0, 1)) AS acum 
     FROM tableRates 
     WHERE id=start_id); 
    RETURN select_var; 
END 

而且他們一個簡單的查詢:

SELECT *, AccumulatedRates(id,@present_id) as acum FROM tableRates; 

其中@present_id作爲參數傳遞。

感謝所有,無論如何!

1

例如:

DROP TABLE IF EXISTS my_table; 

CREATE TABLE my_table 
(id INT NOT NULL PRIMARY KEY 
,rate DECIMAL(5,2) NOT NULL 
); 

INSERT INTO my_table VALUES 
(201704,0.79), 
(201705,0.93), 
(201706,0.81), 
(201707,0.80), 
(201708,0.14); 

SELECT * 
    , CASE WHEN @flag IS NULL THEN @i:=1 ELSE @i:[email protected]+rate END i 
    , @flag:=1 flag 
    FROM my_table 
    , (SELECT @flag:=null,@i:=0) vars 
ORDER 
    BY id DESC; 
+--------+------+-------------+-------+------+------+ 
| id  | rate | @flag:=null | @i:=0 | i | flag | 
+--------+------+-------------+-------+------+------+ 
| 201708 | 0.14 | NULL  |  0 | 1 | 1 | 
| 201707 | 0.80 | NULL  |  0 | 1.80 | 1 | 
| 201706 | 0.81 | NULL  |  0 | 2.61 | 1 | 
| 201705 | 0.93 | NULL  |  0 | 3.54 | 1 | 
| 201704 | 0.79 | NULL  |  0 | 4.33 | 1 | 
+--------+------+-------------+-------+------+------+ 
5 rows in set (0.00 sec)