programing

MySQL 저장 프로시저에서 커서 오류 발생

topblog 2023. 7. 27. 21:33
반응형

MySQL 저장 프로시저에서 커서 오류 발생

이전 판독값에서 현재 판독값을 빼서 사용한 전류의 단위를 기준으로 양을 계산하려고 하는데 구문 오류와 논리 문제가 있는 것 같습니다.제발 도와주세요.

(삽입문 자체에서 수행할 수 있다는 것은 알고 있지만 커서가 어떻게 작동하는지 이해해야 합니다.)

파일의 22행 오류: 'DEF.sql': SQL 구문에 오류가 있습니다. 'LOOP:' 근처에서 사용할 올바른 구문은 MariaDB 서버 버전에 해당하는 설명서에서 확인하십시오.

FETCH curBill INTO cno, pr, cr;
        IF !flag THEN
            SET unt = cr-pr;
        EL' at line 13

MariaDB v10.4.8

CREATE DATABASE Random;
USE Random;

CREATE TABLE Customer(
    `c_no`              INT,
    `name`              VARCHAR(40),
    `previous_reading`  INT,
    `current_reading`   INT,
    `amount`            INT DEFAULT 0
);

INSERT INTO Customer (`c_no`, `name`, `previous_reading`,`current_reading`)
VALUES
    (101, 'Smith', 90, 120),
    (201, 'George', 30, 250),
    (301, 'Philip', 120, 200),
    (401, 'Jasper', 10,390);

SELECT * FROM Customer;

DELIMITER $$ ;
CREATE PROCEDURE e_bills()
BEGIN
    DECLARE flag INT DEFAULT 0;
    DECLARE cno INT;
    DECLARE pr, cr, amt, unt DOUBLE;
    DECLARE curBill
        CURSOR FOR
            SELECT `c_id`, `previous_reading`, `current_reading`
            FROM Customer;
    DECLARE CONTINUE HANDLER FOR NOT found SET flag = 1;

    OPEN curBill;
    calUnit LOOP:
        FETCH curBill INTO cno, pr, cr;
        IF !flag THEN
            SET unt = cr-pr;
        ELSE IF flag THEN
            LEAVE calUnit;
        END IF;
        IF (unt <= 100) THEN
            SET amt = unt*2;
        ELSE IF (unt >= 101 AND unt <= 200) THEN
            SET amt = unt*2.5;
        ELSE IF (unt > 201 AND unt <= 300) THEN
            SET amt = unt*3;
        ELSE IF (unt > 301) THEN
            SET amt = unt*4;
        END IF;
        UPDATE Customer
        SET `amount`=amt;
    END LOOP;
    CLOSE curBill;
END $$
DELIMITER ; $$

CALL e_bills();

SELECT * FROM Customer;

DROP DATABASE Random;

많은 synatx 오류가 발생하고 업데이트 문에서 where 절을 사용하지 않으면 모든 고객이 업데이트됩니다.

drop table if exists t;
CREATE TABLE t(
    `c_no`              INT,
    `name`              VARCHAR(40),
    `previous_reading`  INT,
    `current_reading`   INT,
    `amount`            INT DEFAULT 0
);

INSERT INTO t (`c_no`, `name`, `previous_reading`,`current_reading`)
VALUES
    (101, 'Smith', 90, 120),
    (201, 'George', 30, 250),
    (301, 'Philip', 120, 200),
    (401, 'Jasper', 10,390);

drop procedure if exists p;
DELIMITER $$ 
CREATE PROCEDURE p()
BEGIN
    DECLARE flag INT DEFAULT 0;
    DECLARE cno INT;
    DECLARE pr, cr, amt, unt DOUBLE;
    DECLARE curBill
        CURSOR FOR
            SELECT c_no, `previous_reading`, `current_reading`
            FROM t;
    DECLARE CONTINUE HANDLER FOR NOT found SET flag = 1;

    OPEN curBill;
    calUnit: LOOP
        FETCH curBill INTO cno, pr, cr;
        IF flag <> 1 THEN
            SET unt = cr-pr;
        ELSE
            LEAVE calUnit;
        END IF;
        IF (unt <= 100) THEN
            SET amt = unt*2;
        ELSEIF (unt >= 101 AND unt <= 200) THEN
            SET amt = unt*2.5;
        ELSEIF (unt > 201 AND unt <= 300) THEN
            SET amt = unt*3;
        ELSEIF (unt > 301) THEN
            SET amt = unt*4;
        END IF;
        UPDATE t
        SET `amount`=amt
            where c_no = cno;
    END LOOP;
    CLOSE curBill;
END $$
DELIMITER ; 

CALL p();

SELECT * FROM t;

+------+--------+------------------+-----------------+--------+
| c_no | name   | previous_reading | current_reading | amount |
+------+--------+------------------+-----------------+--------+
|  101 | Smith  |               90 |             120 |     60 |
|  201 | George |               30 |             250 |    660 |
|  301 | Philip |              120 |             200 |    160 |
|  401 | Jasper |               10 |             390 |   1520 |
+------+--------+------------------+-----------------+--------+
4 rows in set (0.00 sec)

언급URL : https://stackoverflow.com/questions/58681160/mysql-stored-procedures-with-cursor-giving-error

반응형