mirror of
https://github.com/MariaDB/server.git
synced 2025-07-30 16:24:05 +03:00
MDEV-10580 sql_mode=ORACLE: FOR loop statement
Adding labeled FOR LOOP
This commit is contained in:
@ -627,3 +627,53 @@ SELECT f1(3, 2) FROM DUAL;
|
||||
f1(3, 2)
|
||||
5
|
||||
DROP FUNCTION f1;
|
||||
# Testing labeled FOR LOOP statement
|
||||
CREATE FUNCTION f1 (a INT, limita INT, b INT, limitb INT) RETURN INT
|
||||
AS
|
||||
total INT := 0;
|
||||
BEGIN
|
||||
<<la>>
|
||||
FOR ia IN 1 .. a
|
||||
LOOP
|
||||
total:= total + 1000;
|
||||
<<lb>>
|
||||
FOR ib IN 1 .. b
|
||||
LOOP
|
||||
total:= total + 1;
|
||||
EXIT lb WHEN ib = limitb;
|
||||
EXIT la WHEN ia = limita;
|
||||
END LOOP lb;
|
||||
END LOOP la;
|
||||
RETURN total;
|
||||
END;
|
||||
/
|
||||
SHOW FUNCTION CODE f1;
|
||||
Pos Instruction
|
||||
0 set total@4 0
|
||||
1 set ia@5 1
|
||||
2 set [upper_bound]@6 a@0
|
||||
3 jump_if_not 17(17) (ia@5 <= [upper_bound]@6)
|
||||
4 set total@4 (total@4 + 1000)
|
||||
5 set ib@7 1
|
||||
6 set [upper_bound]@8 b@2
|
||||
7 jump_if_not 15(15) (ib@7 <= [upper_bound]@8)
|
||||
8 set total@4 (total@4 + 1)
|
||||
9 jump_if_not 11(0) (ib@7 = limitb@3)
|
||||
10 jump 15
|
||||
11 jump_if_not 13(0) (ia@5 = limita@1)
|
||||
12 jump 17
|
||||
13 set ib@7 (ib@7 + 1)
|
||||
14 jump 7
|
||||
15 set ia@5 (ia@5 + 1)
|
||||
16 jump 3
|
||||
17 freturn 3 total@4
|
||||
SELECT f1(2, 1, 2, 2) FROM DUAL;
|
||||
f1(2, 1, 2, 2)
|
||||
1001
|
||||
SELECT f1(2, 2, 2, 2) FROM DUAL;
|
||||
f1(2, 2, 2, 2)
|
||||
2003
|
||||
SELECT f1(2, 3, 2, 3) FROM DUAL;
|
||||
f1(2, 3, 2, 3)
|
||||
2004
|
||||
DROP FUNCTION f1;
|
||||
|
@ -860,3 +860,42 @@ SELECT f1(3, 2) FROM DUAL;
|
||||
f1(3, 2)
|
||||
5
|
||||
DROP FUNCTION f1;
|
||||
# Testing labeled FOR LOOP statement
|
||||
CREATE FUNCTION f1 (a INT, limita INT, b INT, limitb INT) RETURN INT
|
||||
AS
|
||||
total INT := 0;
|
||||
BEGIN
|
||||
<<la>>
|
||||
FOR ia IN 1 .. a
|
||||
LOOP
|
||||
total:= total + 1000;
|
||||
<<lb>>
|
||||
FOR ib IN 1 .. b
|
||||
LOOP
|
||||
total:= total + 1;
|
||||
EXIT lb WHEN ib = limitb;
|
||||
EXIT la WHEN ia = limita;
|
||||
END LOOP lb;
|
||||
END LOOP la;
|
||||
RETURN total;
|
||||
END;
|
||||
/
|
||||
SELECT f1(1, 1, 1, 1) FROM DUAL;
|
||||
f1(1, 1, 1, 1)
|
||||
1001
|
||||
SELECT f1(1, 2, 1, 2) FROM DUAL;
|
||||
f1(1, 2, 1, 2)
|
||||
1001
|
||||
SELECT f1(2, 1, 2, 1) FROM DUAL;
|
||||
f1(2, 1, 2, 1)
|
||||
2002
|
||||
SELECT f1(2, 1, 2, 2) FROM DUAL;
|
||||
f1(2, 1, 2, 2)
|
||||
1001
|
||||
SELECT f1(2, 2, 2, 2) FROM DUAL;
|
||||
f1(2, 2, 2, 2)
|
||||
2003
|
||||
SELECT f1(2, 3, 2, 3) FROM DUAL;
|
||||
f1(2, 3, 2, 3)
|
||||
2004
|
||||
DROP FUNCTION f1;
|
||||
|
@ -485,3 +485,32 @@ SHOW FUNCTION CODE f1;
|
||||
SELECT f1(3, 100) FROM DUAL;
|
||||
SELECT f1(3, 2) FROM DUAL;
|
||||
DROP FUNCTION f1;
|
||||
|
||||
--echo # Testing labeled FOR LOOP statement
|
||||
|
||||
DELIMITER /;
|
||||
CREATE FUNCTION f1 (a INT, limita INT, b INT, limitb INT) RETURN INT
|
||||
AS
|
||||
total INT := 0;
|
||||
BEGIN
|
||||
<<la>>
|
||||
FOR ia IN 1 .. a
|
||||
LOOP
|
||||
total:= total + 1000;
|
||||
<<lb>>
|
||||
FOR ib IN 1 .. b
|
||||
LOOP
|
||||
total:= total + 1;
|
||||
EXIT lb WHEN ib = limitb;
|
||||
EXIT la WHEN ia = limita;
|
||||
END LOOP lb;
|
||||
END LOOP la;
|
||||
RETURN total;
|
||||
END;
|
||||
/
|
||||
DELIMITER ;/
|
||||
SHOW FUNCTION CODE f1;
|
||||
SELECT f1(2, 1, 2, 2) FROM DUAL;
|
||||
SELECT f1(2, 2, 2, 2) FROM DUAL;
|
||||
SELECT f1(2, 3, 2, 3) FROM DUAL;
|
||||
DROP FUNCTION f1;
|
||||
|
@ -931,3 +931,35 @@ DELIMITER ;/
|
||||
SELECT f1(3, 100) FROM DUAL;
|
||||
SELECT f1(3, 2) FROM DUAL;
|
||||
DROP FUNCTION f1;
|
||||
|
||||
|
||||
--echo # Testing labeled FOR LOOP statement
|
||||
|
||||
DELIMITER /;
|
||||
CREATE FUNCTION f1 (a INT, limita INT, b INT, limitb INT) RETURN INT
|
||||
AS
|
||||
total INT := 0;
|
||||
BEGIN
|
||||
<<la>>
|
||||
FOR ia IN 1 .. a
|
||||
LOOP
|
||||
total:= total + 1000;
|
||||
<<lb>>
|
||||
FOR ib IN 1 .. b
|
||||
LOOP
|
||||
total:= total + 1;
|
||||
EXIT lb WHEN ib = limitb;
|
||||
EXIT la WHEN ia = limita;
|
||||
END LOOP lb;
|
||||
END LOOP la;
|
||||
RETURN total;
|
||||
END;
|
||||
/
|
||||
DELIMITER ;/
|
||||
SELECT f1(1, 1, 1, 1) FROM DUAL;
|
||||
SELECT f1(1, 2, 1, 2) FROM DUAL;
|
||||
SELECT f1(2, 1, 2, 1) FROM DUAL;
|
||||
SELECT f1(2, 1, 2, 2) FROM DUAL;
|
||||
SELECT f1(2, 2, 2, 2) FROM DUAL;
|
||||
SELECT f1(2, 3, 2, 3) FROM DUAL;
|
||||
DROP FUNCTION f1;
|
||||
|
@ -3575,6 +3575,30 @@ sp_labeled_control:
|
||||
}
|
||||
while_body pop_sp_loop_label
|
||||
{ }
|
||||
| label_declaration_oracle FOR_SYM
|
||||
{
|
||||
// See "The FOR LOOP statement" comments in sql_lex.cc
|
||||
Lex->sp_block_init(thd); // The outer DECLARE..BEGIN..END block
|
||||
}
|
||||
sp_for_loop_index_and_bounds
|
||||
{
|
||||
if (Lex->sp_push_loop_label(thd, $1)) // The inner WHILE block
|
||||
MYSQL_YYABORT;
|
||||
if (Lex->sp_for_loop_index_and_bounds(thd, $4))
|
||||
MYSQL_YYABORT;
|
||||
}
|
||||
LOOP_SYM
|
||||
sp_proc_stmts1
|
||||
END LOOP_SYM
|
||||
{
|
||||
if (Lex->sp_for_loop_finalize(thd, $4))
|
||||
MYSQL_YYABORT;
|
||||
}
|
||||
pop_sp_loop_label // The inner WHILE block
|
||||
{
|
||||
if (Lex->sp_block_finalize(thd)) // The outer DECLARE..BEGIN..END
|
||||
MYSQL_YYABORT;
|
||||
}
|
||||
| label_declaration_oracle REPEAT_SYM
|
||||
{
|
||||
if (Lex->sp_push_loop_label(thd, $1))
|
||||
|
Reference in New Issue
Block a user