From the translator: I decided to start my journey to Habr not with an attempt to write some unique text from scratch, but with the translation of a relatively fresh (from 08/17/2020) article by the classic PL / SQL development Stephen Feuerstein, in which he discusses the difference in sufficient detail between the two main variants of the PL / SQL function result cache. I hope this translation will be helpful for many developers getting started with Oracle technologies.
Introduction
Sooner or later, any seasoned Oracle developer is asked a question like:
I don't understand what exactly is the difference between deterministic and result_cache. Do they have different use cases? I use deterministic in many functions that get data from lookup tables. Do I need to use the result_cache keyword instead of deterministic?
I thought it would be worth writing about the differences between these two possibilities. First of all, let's make sure we all have the same understanding of when a function is deterministic.
The Wikipedia provides the following definition of a deterministic algorithm:
A deterministic algorithm is an algorithm that returns the same set of outputs for the same set of inputs, while performing the same sequence of actions.
In other words, a deterministic subroutine (procedure or function) has no side effects. By passing a specific set of values ββas input parameters, you will always get the same result at the output, regardless of when, where, or how often you call this subroutine.
A reasonable question is, what is a side effect of a PL / SQL function? At a minimum (the list is not exhaustive):
any (that is, any) DML operator
Using a variable declared outside of this function (that is, global, out-of-scope aka "global")
call any non-deterministic subroutine
, deterministic result_cache , . . ( result_cache), , , .
FUNCTION betwnstr (
string_in IN VARCHAR2
, start_in IN INTEGER
, end_in IN INTEGER
)
RETURN VARCHAR2 DETERMINISTIC
IS
BEGIN
RETURN (SUBSTR (string_in, start_in, end_in - start_in + 1));
END;
- substr
, , . , , .
, Oracle Database , DETERMINISTIC
( ).
?
,
( )
, :
CREATE OR REPLACE FUNCTION pass_number (i NUMBER)
RETURN NUMBER
DETERMINISTIC
IS
BEGIN
DBMS_OUTPUT.put_line ('pass_number executed');
RETURN 0;
END;
/
DECLARE
n NUMBER := 0;
BEGIN
FOR rec IN (SELECT pass_number (1)
FROM all_objects
WHERE ROWNUM < 6)
LOOP
n := n + 1;
END LOOP;
DBMS_OUTPUT.put_line (n + 1);
END;
/
pass_number executed
6
, , 5 , . Oracle Database , ( PL/SQL SQL-, ).
, result_cache
betwnstr
, result_cache:
FUNCTION betwnstr (
string_in IN VARCHAR2
, start_in IN INTEGER
, end_in IN INTEGER
)
RETURN VARCHAR2
RESULT_CACHE
IS
BEGIN
RETURN (SUBSTR (string_in, start_in, end_in - start_in + 1));
END;
- RESULT_CACHE
. , DETERMINISTIC
, . , result_cache.
result_cache? :
Oracle Database, SGA (Shared Global Area)
, ,
( "" )
( Oracle - , references) , commit
, . RESULT_CACHE
- "" DETERMINISTIC
( , ) . RESULT_CACHE
, . RESULT_CACHE
Oracle Live SQL.
, , RESULT_CACHE
:
CREATE OR REPLACE FUNCTION pass_number (i NUMBER)
RETURN NUMBER
RESULT_CACHE
IS
BEGIN
DBMS_OUTPUT.put_line ('pass_number executed for ' || i);
RETURN 0;
END;
/
DECLARE
n NUMBER := 0;
BEGIN
FOR rec IN (SELECT pass_number (100)
FROM all_objects
WHERE ROWNUM < 6)
LOOP
n := n + 1;
END LOOP;
DBMS_OUTPUT.put_line ('All done ' || TO_CHAR (n + 1));
END;
/
pass_number executed for 100
All done 6
BEGIN
DBMS_OUTPUT.PUT_LINE ('Returned ' || pass_number (100));
DBMS_OUTPUT.PUT_LINE ('Returned ' || pass_number (200));
DBMS_OUTPUT.PUT_LINE ('Returned ' || pass_number (300));
DBMS_OUTPUT.PUT_LINE ('Returned ' || pass_number (100));
DBMS_OUTPUT.PUT_LINE ('Returned ' || pass_number (200));
DBMS_OUTPUT.PUT_LINE ('Returned ' || pass_number (300));
END;
/
Returned 0
pass_number executed for 200
Returned 0
pass_number executed for 300
Returned 0
Returned 0
Returned 0
Returned 0
100 ( ), , , .
200 300 - , .
! ( ) PL/SQL , :
All done 6
Returned 0
Returned 0
Returned 0
Returned 0
Returned 0
Returned 0
, RESULT_CACHE
, , . , - - .
: , result_cache, , .
deterministic result_cache?
DETERMINISTIC
RESULT_CACHE
.
?
, , DETERMINISTIC
, ( ) ( SQL-, ). , , .
, , , RESULT_CACHE
, (instance) , ( , ) . , .
?
: DETERMINISTIC
, .
PL/SQL SQL, , (, ).
, . , , .
DETERMINISTIC
, . Oracle , , .
, result_cache?
. RESULT_CACHE
. DBA, , . , SGA , (latch contention).
, result_cache. :
?
, ? ,
, , , ? , ,
- , NLS? , , , ,
TO_CHAR
.
: RESULT_CACHE
, , , .