带有循环

时间:2017-04-11 12:29:11

标签: mysql informix

以下是为Informix编写的存储过程。我想把它翻译成MySQL。我已经解决了IN,OUT变量,但我很难找到错误处理的方法,尽管目前这并不是一个很大的问题。接下来我有一个存储过程调用,它返回三个参数。我想知道这在MySQL中是否可行?最后,我想从结果中构建一个查询,并通过结果循环并在第一次迭代后退出。

程序从这里开始。

CREATE PROCEDURE  "informix".elite_ctrl_date(p_game_code CHAR(10))         
RETURNING DATE,INTEGER,INTEGER,INTEGER,INTEGER,CHAR(1);`    

-- Return Vars
DEFINE  l_date                  DATE;
DEFINE  l_week                  INTEGER;
DEFINE  l_event                 INTEGER;
DEFINE  l_min_event             INTEGER;
DEFINE  l_max_event             INTEGER;
DEFINE  l_dayname               CHAR(3);
DEFINE  l_open                  CHAR(1);

-- Get Current Vars
DEFINE  l_week_now              INTEGER;
DEFINE  l_today                 DATE;
DEFINE  l_now                   DATETIME HOUR TO MINUTE;
DEFINE  l_datetime              DATETIME YEAR TO SECOND;
DEFINE  l_first_score           DATE;
DEFINE  l_dt_first              DATETIME YEAR TO SECOND;


-- Errorlog Stuff
DEFINE  l_return                INTEGER;
DEFINE  l_SQL_error             INTEGER;
DEFINE  l_ISM_error             INTEGER;
DEFINE  l_error_data            CHAR(200);
DEFINE  l_error                 CHAR(300);

ON EXCEPTION SET l_SQL_error, l_ISM_error, l_error_data
    LET l_error = "SQL: " || l_SQL_error || " ISAM: " || l_ISM_error || " Data: " || l_error_data;
    CALL create_errlog( p_game_code,
                        133,        --PV_erl_errno
                        0,          --PV_erl_manager_pin
                        0,          --PV_erl_team_pin
                        l_error,    --PV_erl_notes
                        "Y"         --PV_report
                    )
        RETURNING l_return;
    RETURN "01/01/1980",-133,-133,-133,-133, "N";
END EXCEPTION;

SET ISOLATION TO DIRTY READ;

LET l_first_score   = NULL;
LET l_dt_first      = NULL;
LET l_open          = "N";
LET l_min_event     = -99;

SELECT  DATE(first_score), EXTEND(first_score, YEAR TO SECOND)
INTO    l_first_score, l_dt_first
FROM    game_config
WHERE   game_code = p_game_code;

CALL get_current() RETURNING l_today, l_now, l_datetime;

IF l_first_score IS NOT NULL
    AND l_today < l_first_score
THEN
    LET l_today     = l_first_score;
    LET l_now       = "00:00";
    LET l_datetime  = l_dt_first;
END IF

SELECT  weekno
INTO    l_week_now
FROM    calendar
WHERE   date = l_today;

IF week_now IS NULL
THEN
    LET week_now = -164;
END IF

FOREACH
    SELECT  date,weekno,event,dayname
    INTO    l_date,l_week,l_event,l_dayname
    FROM    event a,calendar b
    WHERE   a.abs_dayno   = b.abs_dayno
    AND     a.date        = l_today
    AND     a.start      >= l_now
    AND     b.weekno     NOT IN (SELECT week FROM international)
    AND     b.weekno     NOT IN (SELECT weekno FROM nonscore_week)
    AND     b.day IN ('Sat','Sun')
    UNION
    SELECT  date,weekno,event,dayname
    FROM    event a,calendar b
    WHERE   a.abs_dayno   = b.dia_abs_dayno
    AND     a.date        > l_today
    AND     b.weekno     NOT IN (SELECT week FROM international)
    AND     b.weekno     NOT IN (SELECT weekno FROM nonscore_week)
    AND     b.day IN ('Sat','Sun')
    UNION
    SELECT  TODAY,9999,9999,"N/A"
    FROM    event,calendar
    WHERE   a.abs_dayno   = b.abs_dayno
    AND     a.event       = (SELECT MAX(event) FROM event)
    AND     b.weekno     NOT IN (SELECT week FROM international)
    AND     b.weekno     NOT IN (SELECT weekno FROM nonscore_week)
    ORDER BY 3

    IF l_event = 9999
    THEN
        LET l_date      = TODAY;
        LET l_week      = -164;
        LET l_event     = -164;
        LET l_max_event = -164;
    END IF

    IF l_week != -164
    THEN
        SELECT  MIN(event)
        INTO    l_min_event
        FROM    event
        WHERE   weekno = l_week
        AND     dayname IN ('Sat','Sun');
    END IF

    IF l_min_event < l_event
    THEN
        CONTINUE FOREACH;
    END IF

    IF l_week != -164
    THEN
        SELECT  MAX(event)
        INTO    l_max_event
        FROM    event
        WHERE   weekno = l_week
        AND     dayname IN ('Sat','Sun');
    END IF

    EXIT FOREACH;

END FOREACH;

SELECT  MIN(event)
INTO    l_min_event
FROM    stan_calendar a, game_event b
WHERE   a.weekno = l_week
AND     a.date = b.date
AND     a.day IN ('Sat','Sun');

IF l_min_event = l_event
THEN
    LET l_open = "Y";
END IF

RETURN l_date,l_week,l_event,l_max_event,l_week_now,l_open;

END PROCEDURE;

这在MySQL中是否可行,或者还有另外一种方法吗? 非常感谢

所以我有这个......

CREATE PROCEDURE `control_date`(in p_game_code char(10),out outDate date, out outWeek int, out outWeekNow int, out outOpen char(1))
BEGIN
DECLARE ld_first    DATE;
DECLARE ldt_first   DATETIME;

DECLARE l_date      DATE;
DECLARE l_time      TIME;
DECLARE l_dtime     DATETIME;

DECLARE l_done      INT;

DECLARE procDate    DATE;
DECLARE procTime    TIME;
DECLARE procWeekNo  INT;

DECLARE noMoreWeeks INT(4);

SET SESSION TRANSACTION ISOLATION LEVEL READ UNCOMMITTED;

SET outOpen = "N";

SELECT DATE(game_start), game_start
INTO ld_first , ldt_first 
FROM gameConfig
WHERE game_code = p_game_code;

SELECT date, time, datetime
INTO l_date , l_time , l_dtime 
FROM time
WHERE 1 = 1;

if (l_date is null)
or (l_time is null)
or (l_dtime is null)
then
    set l_date = now();
    set l_time = now();
    set l_dtime = now();
end if;

if ((ld_first is null)
and (l_date < ld_first))
then
    set l_date = ld_first;
    set l_time = "00:00:00";
    set l_dtime = ldt_first;
end if;

SELECT week_number
INTO outWeekNow 
FROM week_config
WHERE l_date BETWEEN start_date AND end_date;

if outWeekNow IS NULL
then
    SET outWeekNow = -1;
end if;

DECLARE curs1 CURSOR FOR 
    SELECT fixture_date, fixture_time, week_number 
    FROM fixture WHERE fixture_date = l_date
    AND fixture_time >= l_time
    UNION 
    SELECT fixture_date, fixture_time, week_number 
    FROM fixture WHERE fixture_date > l_date 
    UNION 
    SELECT curdate(), curtime(), 9999 
    FROM fixture 
    ORDER BY 3,1,2;

DECLARE CONTINUE HANDLER FOR NOT FOUND SET noMoreWeeks = TRUE;

loopQuery: LOOP
    set l_done = 0;

    open dayCurs;
    fetch dayCurs into procDate, procTime, procWeekNo USING l_date, l_time, l_date;

    if l_done
    then
        LEAVE loopQuery;
    end if;

    if procWeekNo = 9999
    then
        SET procDate = curdate();
        SET procWeekNo = -1;
    end if;

    LEAVE loopQuery;
END LOOP;

if procDate => l_date
then
    if procDate > l_date
    then
        set outOpen = "Y";
    else
        if procTime > l_time
        then
            set outOpen = "Y";
        end if;
    end if;
end if;

set outDate = procDate;
set outWeek = procWeekNo; 
END

但我的代码中有错误。它出现在if语句

if outWeekNow IS NULL
then
SET outWeekNow = -1;
end if;

但我知道它不在这里,因为当我发表评论时,错误会发生变化。如果我在此之前评论一切。评论在BEGIN上。

请问任何想法?

非常感谢。

0 个答案:

没有答案