【问题标题】:MySQL Inner cursor executes only one timeMySQL内部游标只执行一次
【发布时间】:2016-12-24 13:03:52
【问题描述】:
DELIMITER $$

CREATE PROCEDURE `remove_schedule_duplicate` ()
BEGIN
    BLOCK1 : BEGIN 

    DECLARE finished INTEGER DEFAULT 0;
    DECLARE schedule_id CHAR(36);
    DECLARE gamePk INTEGER;
    DECLARE keep_entry TINYINT(1);
    DECLARE scheduleDuplicate CURSOR FOR SELECT game_pk FROM schedule where is_active = 1 group by game_pk,home_team_id,away_team_id,venue_id having count(game_pk) > 1 limit 2;
    DECLARE CONTINUE HANDLER FOR NOT FOUND SET finished = 1;

    OPEN scheduleDuplicate;

    get_schedule_duplicate: LOOP

    FETCH scheduleDuplicate INTO gamePk;

    IF finished = 1 THEN
        LEAVE get_schedule_duplicate;
            END IF;

            **BLOCK2 : BEGIN 

            DECLARE block_finished INTEGER DEFAULT 0;
            DECLARE blockDuplicate CURSOR FOR SELECT id FROM schedule where game_pk = gamePk and is_active = 1;
            DECLARE CONTINUE HANDLER FOR NOT FOUND SET block_finished = 1;

            OPEN blockDuplicate;

            block_schedule_duplicate: LOOP

            FETCH blockDuplicate INTO schedule_id;

            IF block_finished = 1 THEN
                LEAVE block_schedule_duplicate;
                        END IF;

                        IF keep_entry = 0 THEN
                            UPDATE schedule set is_active = 0 where id = schedule_id;
                        END IF;

                    END LOOP block_schedule_duplicate;

                    CLOSE blockDuplicate;

            END BLOCK2;**

        END LOOP get_schedule_duplicate;

        CLOSE scheduleDuplicate;

END BLOCK1;

END 

$$

问题是 Innerloop 第一次执行良好之后 block_finished 总是 1 所以。总是退出内部块。

如何解决此问题。我做什么 ?有人帮我解决这个问题。

【问题讨论】:

  • 不过,我还是找不到原因。所以我用单游标改变了存储过程,在一些条件下达到了上面存储过程的效果。
  • 就像摸头周围的鼻子。 DECLARE scheduleDuplicate CURSOR FOR SELECT game_pk,id FROM schedule where game_pk in (SELECT game_pk FROM schedule where is_active = 1 group by game_pk,home_team_id,away_team_id,venue_id 有 count(game_pk) > 1) and is_active = 1 order by game_pk; DECLARE CONTINUE HANDLER FOR NOT FOUND SET finished = 1;
  • 发布表的结构以及一些测试数据,这样会更容易帮到你。
  • CREATE TABLE schedule (game_id varchar(500) DEFAULT NULL, game_datetimestamp NOT NULL DEFAULT '2016-01-01 00:00:00', game_time timestamp NULL DEFAULT NULL, home_team_id char(36) NOT NULL, away_team_id char(36) NOT NULL, venue_id char(36) 默认 NULL, id char(36) NOT NULL, is_active bit(1) 默认b'1', game_pk int(11) NOT NULL )
  • 插入时间表(game_id,game_date,game_time,home_team_id,away_team_id,venue_id,id,is_active,game_pk)值

标签: mysql stored-procedures cursor


【解决方案1】:

我已经像这样更改了我的存储过程:

DELIMITER $$
CREATE PROCEDURE `remove_schedule_duplicate`()
BEGIN
    DECLARE finished INTEGER DEFAULT 0;
    DECLARE schedule_id,temp CHAR(36) DEFAULT NULL;
    DECLARE gamePk INTEGER;
    DECLARE keep_entry TINYINT(1);
    DECLARE scheduleDuplicate CURSOR FOR SELECT game_pk,id FROM schedule where game_pk in (SELECT game_pk FROM schedule where is_active = 1 group by game_pk,home_team_id,away_team_id,venue_id having count(game_pk) > 1) and is_active = 1 order by game_pk;
    DECLARE CONTINUE HANDLER FOR NOT FOUND SET finished = 1;

    OPEN scheduleDuplicate;

        get_schedule_duplicate: LOOP

        FETCH scheduleDuplicate INTO gamePk,schedule_id;

        IF finished = 1 THEN
            LEAVE get_schedule_duplicate;
        END IF;

        IF ((temp IS NULL) AND (gamePk IS NOT NULL)) OR ((temp IS NOT NULL) AND (temp <> gamePk)) THEN
            SET temp = gamePk;
            SET keep_entry = 1;
        #ELSE IF temp IS NOT NULL AND temp = gamePk THEN
        ELSE
            SET keep_entry = 0;
        END IF;

        IF keep_entry = 0 THEN
                UPDATE schedule set is_active = 0 where id = schedule_id;
        END IF;

        END LOOP get_schedule_duplicate;

    CLOSE scheduleDuplicate;

END$$
DELIMITER ;

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2013-02-26
    • 2021-10-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多