2015-06-30 79 views
0

))大家好,這是我的表...如何基於PostgreSQL part2中的枚舉列總結所有行?

enter image description here

目前即時通訊使用此功能觸發...

IF NEW.timetype = 'Total' THEN 
    SELECT SUM(timeelapse) FROM (SELECT DISTINCT ON (floor(timeindex)::int) floor(timeindex)::int timeindex, timeelapse FROM mytable WHERE pcnum = NEW.pcnum AND fnname = NEW.fnname AND timetype = 'Lap' ORDER BY 1, 2 DESC) alias INTO v_sumtimeelapse_fn; 
    IF FOUND THEN 
     NEW.timeelapse := v_sumtimeelapse_fn; 
    ELSE 
     RAISE EXCEPTION USING MESSAGE = 'There is not any previous row...'; 
    END IF; 
END IF; 

所以每當 '總' 插在timetype列它總結了所有的timeelapse FROM mytable WHERE pcnum = NEW.pcnum AND fnname = NEW.fname AND timetype ='Lap',但只有timeindex具有最高的百分數值(在mytable中,它們將是前三個skyblue高亮度平方= 00:01 :00,00:03:00,00:04:00(1.001,2.003,3.003))並將結果放入NEW.tim eelapse(在MYTABLE這將是第一個藍色突出平方= 00:08:00)

功能正常,使之和,但我想兩個規則添加到它...

  1. 當'Total'被插入時間類型時,如果函數在'開始'之後沒有找到'Lap'(兩者都具有相同的pcnum和fnname),那麼它應該顯示錯誤消息「',沒有任何Lap ......「(在mytable中,它將是紅色突出顯示的正方形)。請注意,fnname ='bbbb'的'開始'之後沒有任何'Lap'的fnname ='bbbb'。我嘗試設置我的功能的話,使用...

    RAISE EXCEPTION USING MESSAGE = 'There is not any previous row...' 
    

,但它只是不工作,如果我在那種情況下插入一個「總」,它簡單的離開NEW.timeelapse空值。

  1. 該函數應該將timeelapse與其所有已設置的規則進行SUM,但僅限於那些位於同一pcnum和fnname的最後(後代)'Total'它將成爲第二個藍色突出顯示的正方形)請注意,它僅累計在最後(下劃線)'Total'之後的timeelapses(在mytable中,它將成爲第四個用skyblue突出顯示的正方形)。

Thanks Advanced。

回答

0

要從計算行中排除早於Total的計算行,可以在附件查詢中使用主鍵。 聲明新變量v_fnserial。 找到和fnname的最後一次出現'Total'的fnserial,並將值賦給v_fnserial。 在主查詢中添加條件fnserial > v_fnserial

當主查詢返回null時,應該引發異常。

IF NEW.timetype = 'Total' THEN 
    SELECT fnserial INTO v_fnserial 
    FROM mytable 
    WHERE timetype = 'Total' AND pcnum = NEW.pcnum AND fnname = NEW.fnname 
    ORDER BY fnserial DESC LIMIT 1; 

    SELECT SUM(timeelapse) FROM (
     SELECT DISTINCT ON (floor(timeindex)::int) floor(timeindex)::int timeindex, timeelapse 
     FROM mytable 
     WHERE fnserial > coalesce(v_fnserial, 0) AND pcnum = NEW.pcnum AND fnname = NEW.fnname AND timetype = 'Lap' 
     ORDER BY 1, 2 DESC) alias 
    INTO v_sumtimeelapse_fn; 
    IF v_sumtimeelapse_fn NOTNULL THEN 
     NEW.timeelapse := v_sumtimeelapse_fn; 
    ELSE 
     RAISE EXCEPTION USING MESSAGE = 'There is not any previous row...'; 
    END IF; 
END IF; 
+0

我這樣做(與fnserial的東西),但包括在主'選擇SUM'一個括號裏面,像這樣...'選擇SUM(timeelapse) FROM(SELECT DISTINCT ON(地板( timeindex):: int)floor(timeindex):: int timeindex,timeelapse FROM mytable WHERE pcnum = NEW.pcnum AND fnname = NEW.fnname AND timetype ='Lap'AND fnserial>(SELECT fnserial FROM mytable WHERE pcnum = NEW。 pcnum AND fnname = NEW.fnname AND timetype ='Total'ORDER BY fnserial DESC LIMIT 1)ORDER BY 1,2 DESC)別名INTO v_sumtimeelapse_perfn; 如果FOUND THEN',但它不是SUM最後的'總是的,可以嗎?謝謝 – litu16

+0

也在函數的結尾,我使用了'IF FOUND THEN'而不是'IF v_sumtimeelapse_fn NOTNULL THEN'它可以嗎? THanks – litu16

+0

我一直在嘗試使用'IF v_sumtimeelapse_fn NOTNULL THEN'來代替'IF FOUND THEN'。但是這個函數有一個bug,它只有在表中有相同的fnname和timetype的前一個'Total'時才起作用,如果沒有任何前一個,它會發送'RAISE EXCEPTION USING MESSAGE'我們能做什麼??? THanks – litu16