在Teradata中结束交易后是否需要提交COMMIT?

时间:2019-02-08 14:57:13

标签: teradata

我有一个存储过程,可以从表中读取行,对每行进行一些计算,然后将结果存储在同一行中。

当我需要处理一百万行时,所有UPDATES都在填充DBC数据库,因此我想在1000行计算之后执行COMMIT。

我需要使用交易还是需要使用COMMIT? 提交工作是做什么的?

我在TERA模式下执行所有操作,版本为15.00。

这是简化我的程序的示例:

-- Creates a sample table
--DROP TABLE DM_CALIDAD.RGR_TEST_PROCEDURE;
CREATE MULTISET TABLE DM_CALIDAD.RGR_TEST_PROCEDURE AS(
SELECT T.TABLENAME AS "TABLE_NAME", 0(INTEGER) AS IND_NAME FROM DBC.TABLESV T
)WITH DATA
;

--Creates the procedure
REPLACE PROCEDURE DM_CALIDAD.SP_TEST_NAME()
BEGIN

    DECLARE V_TABLE_NAME VARCHAR(256) DEFAULT NULL;
    DECLARE V_CALC INTEGER;
    DECLARE SQL_CURSOR1, SQL_UPDATE VARCHAR(10000) DEFAULT NULL;
    DECLARE CONT INTEGER DEFAULT NULL;

    DECLARE CUR_CURSOR1 CURSOR FOR PREP_CURSOR1;

    SET SQL_CURSOR1 = 'SELECT TABLE_NAME FROM DM_CALIDAD.RGR_TEST_PROCEDURE';

    SET CONT = 1;
    PREPARE PREP_CURSOR1 FROM SQL_CURSOR1;
    OPEN CUR_CURSOR1;

    BEGIN TRANSACTION;
    l_loop: 
    LOOP

        FETCH CUR_CURSOR1 INTO V_TABLE_NAME;

        IF (SQLCODE <> 0) THEN
            LEAVE l_loop;
        END IF;

        SET SQL_UPDATE = 'UPDATE DM_CALIDAD.RGR_TEST_PROCEDURE SET IND_NAME = IND_NAME+1 WHERE TABLE_NAME = ''' ||V_TABLE_NAME || '''';
        EXECUTE IMMEDIATE SQL_UPDATE;

        -- Ends the transacion each 1000 updates 
        SET CONT = CONT + 1;
        IF (CONT MOD 1000 = 0) THEN
            END TRANSACTION;
            --COMMIT WORK;
            BEGIN TRANSACTION;
        END IF;

    END LOOP l_loop;
    END TRANSACTION;
    CLOSE CUR_CURSOR1;

END;

-- Calls procedure
CALL DM_CALIDAD.SP_TEST_NAME();

谢谢。


Edit1,更多详细信息。

我真正要计算的是考虑到每个城市的银行假期(或节日)和周末,两个日期之间有多少个工作日。

例如,我正在将某物从A发送到B,并且我有一个跟踪事件说它在2月1日(星期五)在A,在2月6日(下一个星期三)在B,因此对于BI,需要查询这些日期之间的所有日子都在寻找节日。

对于这个提议,我有一张桌子,桌子上有2列,分别是城市和节日。

CITY | FESTIVE
  B    2019-02-02 -- For being Saturday
  B    2019-02-03 -- For being Sunday
  B    2019-02-04 -- For being festive at B

因此,对于每一行,我读取列 first_event 和列 last_event 并进行差值(6-1 = 5days),然后计算出B的休息日 (SELECT COUNT(*) FROM FESTIVES_TABLE WHERE CITY='B' AND FESTIVE BETWEEN DATE '2019-02-01' AND DATE '2019-02-06'),它返回3天,然后我将它们减去5天(06天-01天= 5天,5天-3节日= 2天)。

所以劳动天数是2,然后用计算出的值更新行。

我已经检查了DBC数据库的烫发空间,它具有1962GB。

再次感谢:)

1 个答案:

答案 0 :(得分:1)

有一种非常简单的方法来计算工作日(或假日)的天数,而无需循环/计数/等,它是基于日历表中计算出的business_day数列。在您的情况下,它稍微复杂一点,因为您需要多个日历,每个城市一个。

因此,让我们在视图中进行计算(或使用通用表表达式WITH my_cal AS SELECT ...):

REPLACE VIEW my_cal AS
SELECT c.*,
  -- running business day number
  -- increases only for each business day
  Sum(CASE WHEN f.festive IS NULL THEN 1 ELSE 0 end)
  Over (PARTITION BY c.city
        ORDER BY c.caldt
        ROWS Unbounded Preceding) AS business_day_num
FROM 
 ( -- this simply create all dates for each city
   SELECT *
   FROM 
    ( -- all cities
      SELECT DISTINCT city
      FROM festivetable
    ) AS f
   CROSS JOIN 
    ( -- all dates
      SELECT calendar_date AS caldt
      FROM sys_calendar.CALENDAR AS c -- you should use your company's calendar instead
      WHERE caldt BETWEEN DATE '2018-10-01' AND DATE '2019-02-28' 
    ) AS c
 ) AS c
LEFT JOIN festivetable AS f
  ON  c.city = f.city
 AND c.caldt = f.festive;

现在,在start_date / end_date只需两个联接并计算差异。

SELECT ...
   end_cal.business_day_num - start_cal.business_day_num AS duration_in_business_days
FROM mytable
JOIN my_cal AS start_cal
  ON mytable.city = start_cal.city
 AND mytyble.first_event = start_cal.caldt
JOIN my_cal AS end_cal
  ON mytable.city = end_cal.city
 AND mytyble.first_event = end_cal.caldt

关于DBC,当您说所有UPDATES都在填充DBC数据库时,您是指《瞬态日志》吗?好吧,这可能比dbc大得多(如果系统上有可用空间)。

但是dbc的2TB彼尔姆空间非常低(除非您的系统非常小),目标表有多大,并且要更新的行百分比是什么?