PL SQL Quick Reference
PL SQL Quick Reference
ORACLE:
PL/SQL
QUICK
REFERENCE
By:
Gajendra Reddy Atla
1. INTRODUCTION TO PL/SQL 4
About PL/SQL
Advantages of PL/SQL
PL/SQL Execution Environment
PL/SQL block structure
PL/SQL Block types
Parameters
2. VARIABLES 9
3. CONTROL STRUCTURES 12
Conditional Control
Iterative Control
Sequential Control
4. CURSORS 17
Types of Cursors
Difference B/W Normal Cursor & Ref Cursor
Cursor For Loop
Cursor with Return statement
Cursor attributes
5. PACKAGES 22
Introduction
Advantages
Package Components
Types of Packages
Creating New Package
Referencing Package Components
Using Oracle Supplied Packages
6. TRIGGERS 26
Introduction
Parts of a Trigger
Types of Triggers
Order of Trigger Firing
Dropping, Disabling and Enabling
Examples
7. EXCEPTION HANDLING 32
Introduction
Predefined Exception
User-defined Exception
RAISE_APPLICATION_ERROR
WHEN OTHERS Clause
SQLCODE and SQLERRM
Raising Exceptions
8. COLLECTIONS 35
Introduction
Nested Table
Varray
Index-By Table
Collection Methods
Bulk Collect
9. OVERLOADING 40
1. INTRODUCTION TO PL/SQL
About PL/SQL:
PL/SQL stands for Procedural Language/SQL.
Pl/SQL is the procedural extension to SQL with design features of programming languages.
Data manipulation and query statements of SQL are included with in procedural units of code.
The basic unit in PL/SQL is a block.
All PL/SQL programs are made up of blocks, which can be nested within each other.
Typically, each block performs a logical action in the program.
Advantages of PL/SQL:
PL/SQL is a completely portable, high-performance transaction processing language that offers the
following advantages:
1) Support for SQL.
2) Higher productivity.
3) Better performance.
4) Portability.
5) Integration with Oracle.
6) Modularize program development.
a) We can Group logically related statements with in blocks.
b) We can place reusable PL/SQL code for future use in libraries.
7) Programming with control structures. (Like for, while loops).
SQL is non-procedural, meaning that you can state what you want done without stating how to do it.
Oracle determines the best way to carry out your request. There is no necessary connection between
consecutive statements because Oracle executes SQL statements one at a time.
PL/SQL lets you use all the SQL data manipulation, cursor control, and transaction control commands, as
well as all the SQL functions, operators, and pseudo columns. So, you can manipulate Oracle data flexibly
and safely.
Higher Productivity:
PL/SQL adds functionality to non-procedural tools such as Oracle Forms and Oracle Reports. With
PL/SQL in these tools, you can use familiar procedural constructs to build applications. For example, you
can use an entire PL/SQL block in an Oracle Forms trigger. You need not use multiple trigger steps,
macros, or user exits. Thus, PL/SQL increases productivity by putting better tools in your hands.
Moreover, PL/SQL is the same in all environments. As soon as you master PL/SQL with one Oracle tool,
you can transfer your knowledge to other tools, and so multiply the productivity gains. For example,
scripts written with one tool can be used by other tools.
Better Performance
Without PL/SQL, Oracle must process SQL statements one at a time. Each SQL statement results in
another call to Oracle and higher performance overhead. In a networked environment, the overhead can
The call to the oracle engine needs to be made only once to execute any number of SQL statements, if
these SQL statements are bundled inside a PL/SQL block.
1. PROCEDURE:
PL/SQL procedures behave very much like procedures in other programming language.
Procedures are traditionally the workhorse of the coding world.
Simple Procedure
/* Finds the given number is odd or even */
create or replace procedure prc_even_odd(i_number in number,
o_result out varchar2)
is
begin
if (mod(i_number,2) = 0) then
o_result := 'EVEN';
else
o_result := 'ODD';
end prc_even;
The first one is bind variable declaration. We need to supply some bind variables to the procedures at
the time their calling to capture the output data. The print command prints the data held by variable a.
2. FUNCTION:
Functions are traditionally the smaller, more specific pieces of code.
Functions must return a value.
Simple Function
/* Calculates simple Interest */
create or replace function f_sim_intr(p in number,
t in number,
r in number) return number
is
si number(10);
begin
si:=(p*t*r)/100;
return si;
end;
5 Functions used for calculation purpose Used for data processing purpose
To overcome all these The PL/SQL has one more block called “Anonymous Block”.
3 ANONYMOUS BLOCK:
Anonymous blocks are unnamed PL/SQL blocks. The anonymous block is missing the header section
altogether. Instead it simply uses the DECLARE reserved word to mark the beginning of its optional
declaration section. Anonymous blocks can also serve as nested blocks inside procedures, functions, and
other anonymous blocks.
Anonymous Block
declare
a number;
b varchar2(10);
begin
b := fn_test(101,a);
dbms_output.put_line(b);
dbms_output.put_line(a);
end;
Parameters:
Named PL/SQL programs (procedures and functions) can take parameters.
Parameters are named variables that are available to a program and that modify program
behavior and/or data.
Parameters are optional on both procedures and functions.
Parameters are declared when a procedure or function are declared and are declared between an
open and a close parenthesis (()).
There are three types of parameter:
1. IN
2. OUT and
3. IN OUT
1) An IN parameter is used an input only. An IN parameter cannot be changed by the called
program.
2) An OUT parameter is initially NULL. The program assigns the parameter a value and that value
is returned to the calling program.
3) An IN OUT parameter may or may not have an initial value. That initial value may or may not
be modified by the called program. Any changes made to the parameter are returned to the
calling program.
Parameters are declared with data types but without data type length or precision. That means that
a parameter may be declared as VARCHAR2 but it will not be declared with a length component
Information is transmitted between a PL/SQL program and the database through variables. Every
variable has a specific type associated with it.
Types of variables:
S.No Type Sub Type
Scalar
Composite
3 Declaring a variable with an initial value (not a Message varchar2 (10):= 'Example';
constant):
1. BFILE (Binary File): Large binary objects stored in operating system files outside of the database;
for example, a bitmap image file.
2. BLOB (Binary large object): Large objects consisting of unstructured binary data.
3. CLOB (Character large object): Large objects consisting of single-byte fixed-width character data.
4. NCLOB (National language character large object): Large binary objects consisting of single-byte
or multiple-byte fixed-width character data.
Once a value is set, you can show it with the PRINT command.
print bv;
3. CONTROL STRUCTURES
This chapter shows you how to structure the flow of control through a PL/SQL program. You learn
how statements are connected by simple but powerful control structures that have a single entry and exit
point. Collectively, these structures can handle any situation. Their proper use leads naturally to a well-
structured program.
According to the structure theorem, any computer program can be written using the basic control
structures shown in Figure. They can be combined in any way necessary to deal with a given problem.
Control Structures:
CONDITIONAL CONTROL:
Often, it is necessary to take alternative actions depending on circumstances. The IF statement lets
you execute a sequence of statements conditionally. That is, whether the sequence is executed or not
IF-THEN-END IF
create or replace procedure prc_cs
is
n number;
begin
dbms_output.put_line('Enter any number');
n:=&number;
if n>5 then
dbms_output.put_line('Entered number is greater than 5');
end if;
End;
IF-THEN-ELSE-END IF
create or replace procedure prc_cs
is
n number;
begin
dbms_output.put_line('Enter any number');
n:=&number;
if n>5 then
dbms_output.put_line('Entered number greater than 5');
else
dbms_output.put_line('Entered number less than 5');
end if;
end;
IF-THEN-ELSEIF-ELSE-END IF
create or replace procedure prc_test
is
day varchar2(3):=to_char(sysdate,'dy');
begin
if day='sat' then
ITERATIVE CONTROL:
LOOP statement executes the body statements multiple times. The statements are placed between
LOOP – END LOOP keywords. EXIT statement is used inside LOOP to terminate it.
BASIC LOOP
create or replace procedure prc_num
is
n number:=0;
begin
loop
dbms_output.put_line(n);
FOR LOOP
create or replace procedure prc_num1
is
n number:=0;
begin
for i in 1..100 loop
dbms_output.put_line(n);
n:=n+1;
end loop;
end;
WHILE LOOP
create or replace procedure prc_num1
is
n number:=0;
begin
while n<100 loop
dbms_output.put_line(n);
n:=n+1;
end loop;
end;
SEQUENTIAL CONTROL:
Unlike the IF and LOOP statements, the GOTO and NULL statements are not crucial to PL/SQL
programming. The GOTO statement is seldom needed. Occasionally, it can simplify logic enough to
warrant its use. The NULL statement can improve readability by making the meaning and action of
conditional statements clear.
1). GOTO: The GOTO statement branches to a label unconditionally. The label must be unique within its
scope and must precede an executable statement or a PL/SQL block. When executed, the GOTO statement
transfers control to the labeled statement or block. The labeled statement or block can be down or up in the
sequence of statements.
GOTO Statement
create or replace procedure prc_goto is
n number;
begin
dbms_output.put_line('Enter any Number');
n:=&number;
if n>10 then
goto print;
end if;
dbms_output.put_line('less than 10');
<<print>>
dbms_output.put_line('Greater than 10');
end;
2). NULL: The NULL statement does nothing, and passes control to the next statement. Some languages
refer to such an instruction as a no-op (no operation).
NULL Statement
create or replace procedure prc_cs
is
n number;
begin
dbms_output.put_line('Enter any number');
n:=&number;
if n>5 then
dbms_output.put_line('Entered number greater than 5');
else
NULL;
end if;
end;
4. CURSORS
The Cursor is a handle (name or a pointer) for the memory associated with a specific statement. A
cursor is basically an Area allocated by Oracle for executing the Sql Statements. Every SQL statement
executed by the RDBMS has a private SQL area that contains information about the SQL statement and
the set of data returned. In PL/SQL, a cursor is a name assigned to a specific private SQL area for a
specific SQL statement. There can be either static cursors, whose SQL statement is determined at compile
time, or dynamic cursors, whose SQL statement is determined at runtime.
It is a temporary memory location.
Used to hold the transactional data in the logical memory.
It is valid in PL/SQL block only.
It is not stored in the database permanently.
It is not a reusable component.
Types of Cursors:
S.No TYPES OF CURSORS
1 Implicit Cursor -------
a). Simple cursor
2 Explicit Cursor b). Parameterized cursor
c). Ref Cursor
d). Cursor With Return
Statement
SELECT statements handle the %FOUND and %NOTFOUND attributes differently from explicit
cursors. When an implicit SELECT statement does not return any rows, PL/SQL immediately raises the
NO_DATA_FOUND exception and control passes to the exception section. When an implicit SELECT
returns more than one row, PL/SQL immediately raises the TOO_MANY_ROWS exception and control
passes to the exception section.
Declaring a cursor is possible through CURSOR statement. Opening a cursor is possible through
OPEN statement. Fetching rows from the cursor is possible through FETCH statement. Closing a cursor is
possible through CLOSE statement. So, it is very easy to remember all four operations with the
cursor. These four options are all automatically handled by Oracle in the case of IMPLICIT cursor (like
implicit FOR loop with SELECT).
Parameterized cursor
create or replace procedure prc_cur_details(i_location in dept.loc%type)
is
cursor c_loc is select deptno
from dept
where loc = i_location;
cursor c_emp(l_deptno dept.deptno%type) is select *
from emp
where deptno = l_deptno;
begin
for rec_loc in c_loc loop
for rec_emp in c_emp(rec_loc.deptno) loop
dbms_output.put_line(rec_emp.deptno ||' '||rec_emp.empno||' '||rec_emp.ename);
end loop;
end loop;
end;
A REF CURSOR is majorly used when we want to execute a dynamic select statement causes to
retrieve more than one record. We can pass Ref cursor result as a out parameter which can be used in other
subprograms.
PL/SQL Quick Reference By A.G.Reddy
19
Reference cursors have 2 types.
1. Strong cursors and
2. Week-cursors
In strong cursor we given return type. In week cursor no return type
Ref Cursor
1 create or replace procedure prc_ref(i_deptno in dept.deptno%type
2 ,o_result out sys_refcursor)
3 is
4 begin
5 open o_result for select empno
6 ,ename
7 ,sal
8 ,job
9 ,hiredate
10 from emp
11 where deptno = i_deptno;
12 end;
1 Doesn't have return type. Have a return type. Basically a data type
2 Normal cursors are static cursors. Ref cursors are Dynamic cursors.
3 We can't able to pass like parameter. Ref cursor used for passing cursor parameter.
4 The SQL query has to be defined at The cursor declaration is not associated with any
the time of declaring the cursor itself. SQL query; it is associated with a query at a
later stage this brings in a lot of flexibility as
different SQL queries can be associated with the
cursor.
5 Explicit cursors are generally used to Ref cursor is a cursor variable that point to any
work with more than one row cursor, mainly used for returning the cursor
output.
Cursor For Loop:
A cursor FOR loop is a loop that is associated with (actually defined by) an explicit cursor or a
SELECT statement incorporated directly within the loop boundary. Use the cursor FOR loop whenever
(and only if) you need to fetch and process each and every record from a cursor. The CURSOR FOR Loop
will terminate when all of the records in the cursor have been fetched.
The beauty of using a PL/SQL cursor FOR LOOP is that Oracle automatically Opens the cursor,
the results are automatically Fetched and when all rows have been returned, Oracle automatically Closes
the cursor for you.
Since these steps are almost always followed, Oracle provides a way to let PL/SQL perform most
of the steps. This is called the CURSOR FOR loop. As in the name, it uses a FOR loop to process the
cursor.
Cursor attributes:
Cursor attributes are variables that take some value about the status of the cursor. These values are
automatically set by Oracle and the programmer can read them not write values for them. There are four
cursor attributes. They are
1. %FOUND
2. %IS OPEN
3. %NOTFOUND
4. %ROWCOUNT
1. %FOUND:
After a cursor is opened before the first fetch, the value of this variable is null. After the first fetch,
if the query returns one or more rows as result set, this variable is set to TRUE. When a fetch is made after
the last row of the result set is reached, this variable is set to FALSE.
This variable is extensively used to in stored procedures to handle exceptions when a query returns
no data set. If this variable is referenced before the cursor is opened, an exception INVALID_CURSOR is
raised.
2. %ISOPEN
This variable is set to TRUE if a cursor is opened and false when the cursor is closed.
3. %NOTFOUND
This variable is a logical opposite of %FOUND. This variable is set to TRUE if the last fetch
returns no rows an FALSE when the last fetch returns a row. This can also be used in exception handing
when a query returns no rows.
4. %ROWCOUNT
This variable acts like a counter. It is set to zero when a cursor is opened. Thereafter, with each
fetch, the value of this variable is incremented by 1 if the fetch returns a row. This variable is handy when
processing needs to be done for only a few rows of the result set.
5. PACKAGES
Introduction:
A package is a collection of PL/SQL elements that are "packaged" or grouped together within a
special BEGIN-END syntax, a kind of "meta-block." Here is a partial list of the kinds of elements you can
place in a package:
1. Cursors
2. Variables (scalars, records, tables, etc.) and constants
3. Exception names and pragmas for associating an error number with an exception
4. PL/SQL table and record TYPE statements
5. Procedures and functions
Packages are among the least understood and most underutilized features of PL/SQL. That's a
shame because the package structure is also one of the most useful constructs for building well-designed
PL/SQL-based applications. Packages provide a structure to organize your modules and other PL/SQL
elements. They encourage proper structured programming techniques in an environment that often
befuddles the implementation of structured programming. When you place a program unit into a package
you automatically create a "context" for that program. By collecting related PL/SQL elements in a
package, you express that relationship in the very structure of the code itself. Packages are often called
"the poor man's objects" because they support some, but not all, object-oriented rules.
Advantages:
Packages have many advantages over standalone procedures and functions. For example, they:
Let you organize your application development more efficiently.
Let you grant privileges more efficiently.
Let you modify package objects without recompiling dependent schema objects.
Enable Oracle to read multiple package objects into memory at once.
Let you overload procedures or functions. Overloading means creating multiple procedures with
the same name in the same package, each taking arguments of different number or data type.
Can contain global variables and cursors that are available to all procedures and functions in the
package.
Package Components:
The specification is the interface to your application; it declares the types, variables, constants,
exceptions, cursors, and subprograms available for use. The specification holds public declarations that are
visible to your application.
The body fully defines cursors and subprograms, and so implements the specification. The body holds
implementation details and private declarations that are hidden from your application.
Unlike subprograms, packages cannot be called, parameterized, or nested. However, the formats of
a package and a subprogram are similar. You can debug, enhance, or replace a package body without
changing the specification. You can change a package body without recompiling calling programs because
the implementation details in the body are hidden from your application.
Types of Package:
Although any PL/SQL package must have the same structure and follow the same rules, there are
different types of packages that will play different roles in your application.
1). Create the package specification with the CREATE PACKAGE statement:
You can declare program objects in the package specification. Such objects are called public
objects. Public objects can be referenced outside the package, as well as by other objects in the package.
2). Create the package body with the CREATE PACKAGE BODY statement.
You can declare and define program objects in the package body.
Example1:
The following example shows a package specification for a package named pck_const.
Package Specification
create or replace package pck_const is
end pck_const;
The body for this package defines the prc_test procedure as follows:
Package Body
create or replace package body pck_const is
Example2:
The following example shows a package specification for a package named Employee_Management. The
package contains one stored function and two stored procedures.
Package Specification
Package Body
/*The function accepts all arguments for the fields in the employee table except for the
employee number. A value for this field is supplied by a sequence. The function returns the
sequence number generated by the call to this function.*/
new_empno NUMBER(10);
BEGIN
SELECT emp_sequence.NEXTVAL INTO new_empno FROM dual;
INSERT INTO emp VALUES (new_empno, name, job, mgr,
hiredate, sal, comm, deptno);
RETURN (new_empno);
END hire_emp;
BEGIN
DELETE FROM emp WHERE empno = emp_id;
IF SQL%NOTFOUND THEN
raise_application_error(-20011, 'Invalid Employee
Number: ' || TO_CHAR(emp_id));
END IF;
END fire_emp;
BEGIN
-- If employee exists, then update salary with increase.
END employee_management;
Certain packages are not installed automatically. For these packages Special installation instructions
are needed.
To call a PL/SQL function from SQL, you must either own the function or have EXECUTE privileges
on the function. To select from a view defined with a PL/SQL function, you must have SELECT privileges
on the view. No separate EXECUTE privileges are needed to select from the view.
6. TRIGGERS
Introduction:
Triggers are a special PL/SQL construct similar to procedures. However, a procedure is executed
explicitly from another block via a procedure call, while a trigger is executed implicitly whenever the
triggering event happens. The triggering event is either a INSERT, DELETE, or UPDATE command. The
timing can be either BEFORE or AFTER. The trigger can be either row-level or statement-level, where the
former fires once for each row affected by the triggering statement and the latter fires once for the whole
statement.
Below figure shows a database application with some SQL statements that implicitly fire several
triggers stored in the database. Notice that the database stores triggers separately from their associated
tables.
PARTS OF A TRIGGER:
A trigger has three basic parts:
1. A triggering event or statement
2. A trigger restriction
3. A trigger action
An INSERT, UPDATE, or DELETE statement on a specific table (or view, in some cases)
A CREATE, ALTER, or DROP statement on any schema object
A database startup or instance shutdown
A specific error message or any error message
A user logon or logoff
If the triggers are row triggers, the statements in a trigger action have access to column values of the
row being processed by the trigger. Correlation names provide access to the old and new values for each
column.
PL/SQL Quick Reference By A.G.Reddy
28
TYPES OF TRIGGERS:
This section describes the different types of triggers:
1. Row Triggers and Statement Triggers
2. BEFORE and AFTER Triggers
3. INSTEAD OF Triggers
4. Triggers on System Events and User Events
1). Row Triggers and Statement Triggers
When you define a trigger, you can specify the number of times the trigger action is to be run:
Once for every row affected by the triggering statement, such as a trigger fired by an UPDATE
statement that updates many rows
Once for the triggering statement, no matter how many rows it affects
Row Triggers:
A row trigger is fired each time the table is affected by the triggering statement. For example, if an
UPDATE statement updates multiple rows of a table, a row trigger is fired once for each row affected by
the UPDATE statement. If a triggering statement affects no rows, a row trigger is not run.
Row triggers are useful if the code in the trigger action depends on data provided by the triggering
statement or rows that are affected. For example, Figure 17-3 illustrates a row trigger that uses the values
of each row affected by the triggering statement.
Statement Triggers:
A statement trigger is fired once on behalf of the triggering statement, regardless of the number of
rows in the table that the triggering statement affects, even if no rows are affected. For example, if a
DELETE statement deletes several rows from a table, a statement-level DELETE trigger is fired only
once.
Statement triggers are useful if the code in the trigger action does not depend on the data provided by
the triggering statement or the rows affected. For example, use a statement trigger to:
Make a complex security check on the current time or user
Generate a single audit record
BEFORE and AFTER triggers fired by DML statements can be defined only on tables, not on views.
However, triggers on the base tables of a view are fired if an INSERT, UPDATE, or DELETE statement is
issued against the view. BEFORE and AFTER triggers fired by DDL statements can be defined only on
the database or a schema, not on particular tables.
BEFORE Triggers:
BEFORE triggers run the trigger action before the triggering statement is run. This type of trigger is
commonly used in the following situations:
When the trigger action determines whether the triggering statement should be allowed to
complete. Using a BEFORE trigger for this purpose, you can eliminate unnecessary processing
AFTER Triggers:
AFTER triggers run the trigger action after the triggering statement is run.
BEFORE statement trigger: Before executing the triggering statement, the trigger action is
run.
BEFORE row trigger: Before modifying each row affected by the triggering statement and
before checking appropriate integrity constraints, the trigger action is run, if the trigger
restriction was not violated.
AFTER row trigger: After modifying each row affected by the triggering statement and
possibly applying appropriate integrity constraints, the trigger action is run for the current row
provided the trigger restriction was not violated. Unlike BEFORE row triggers, AFTER row
triggers lock rows.
AFTER statement trigger: After executing the triggering statement and applying any
deferred integrity constraints, the trigger action is run.
You can write normal INSERT, UPDATE, and DELETE statements against the view and the
INSTEAD OF trigger is fired to update the underlying tables appropriately. INSTEAD OF triggers are
activated for each row of the view that gets modified.
4). Triggers on System Events and User Events
You can use triggers to publish information about database events to subscribers. Applications can
subscribe to database events just as they subscribe to messages from other applications. These database
events can include:
System events
Database startup and shutdown
Server error message events
User events
User logon and logoff
DDL statements (CREATE, ALTER, and DROP)
DML statements (INSERT, DELETE, and UPDATE)
Dropping Triggers:
To drop a trigger:
drop trigger <trigger_name>;
Disabling/Enabling Triggers:
To disable or enable a trigger:
alter trigger <trigger_name> {disable|enable};
TRIGGER EXAMPLES:
TRIGGER EXAMPLE#1
TRIGGER EXAMPLE#2
begin
if inserting then
insert into audit_log(user_name
,date1
,action)
values(USER
,sysdate
,'INSERT');
elsif updating then
insert into audit_log(user_name
,date1
,action)
values(USER
,sysdate
,'UPDATE');
elsif deleting then
insert into audit_log(user_name
,date1
,action)
values(user
,sysdate
,'DELETE');
end if;
commit;
end trg_student;
7. EXCEPTION HANDLING
INTRODUCTION:
An exception is an abnormal situation which becomes an obstacle in the normal flow of the
program. When you are writing a PL/SQL block which is a procedural extension of SQL, there comes the
following sequence of blocks:
1). Declare. 2) Begin.3). Exception, 4). End
In the exception block we have to define a user defined Exception handler or system defined
handler to track the error occurred line. This is called Exception handling in Oracle which helps to handle
datatype discrepancies or Constraint type problems or any other kinds of abnormal situations.
When an exception occurs (is raised) in a PL/SQL block, its execution section immediately
terminates. Control is passed to the exception section.
PREDEFINED EXCEPTION:
Predefined exception is raised automatically whenever there is a violation of Oracle coding rules.
Predefined exceptions are those like ZERO_DIVIDE, which is raised automatically when we try to divide
a number by zero. Other built-in exceptions are given below. You can handle unexpected Oracle errors
using OTHERS handler. It can handle all raised exceptions that are not handled by any other handler. It
must always be written as the last handler in exception block.
Predefined exception handlers are declared globally in package STANDARD. Hence we need not
have to define them rather just use them. Every exception in PL/SQL has an error number and error
message; some exceptions also have names as below:
01422 06531
9 19
ORA- ZERO_DIVIDE ORA- SUBSCRIPT_OUTSIDE_LIMIT
01476 06532
10 20
ORA- SUBSCRIPT_BEYOND_COUNT
06533
ZERO_DIVIDE Exception
create or replace procedure prc_zero
Is
N number;
Begin
N:=10/0;
Exception
When ZERO_DIVIDE then
dbms_output.put_line(‘Zero Devide Error’);
end;
NO_DATA_FOUND Exception
create or replace procedure prc_emp_details(i_eno in number,
Name out varchar2,
Salary out number,
Dept out number)
Is
Begin
Select ename, sal, deptno into name, salary, dept
From emp
Where empno=i_eno;
Exception
When NO_DATA_FOUND then
dbms_output.put_line(‘Employee number does not exists’);
end;
USER-DEFINED EXCEPTION:
A User-defined exception has to be defined by the programmer. User-defined exceptions are
declared in the declaration section with their type as exception. They must be raised explicitly using
RAISE statement, unlike pre-defined exceptions that are raised implicitly. RAISE statement can also be
used to raise internal exceptions.
User-defined exception:
RAISE_APPLICATION_ERROR:
To display your own error messages one can use the built-in RAISE_APPLICATION_ERROR.
They display the error message in the same way as Oracle errors. You should use a negative number
between –20000 to –20999 for the error number and the error message should not exceed 512 characters.
RAISE_APPLICATION_ERROR:
RAISING EXCEPTIONS:
With the above explanation it is clear that an exception can be raised in three ways:
1. By the PL/SQL runtime engine
2. By an explicit RAISE statement in your code
3. By a call to the built-in function RAISE_APPLICATION_ERROR
8. COLLECTIONS
INTRODUCTION:
Just about all modern programming languages provide support for collections. A collection can be
loosely defined as a group of ordered elements, all of the same type that allows programmatic access to its
elements through an index. Commonly used collection types used in the programming world include
arrays, maps, and lists.
Probably the biggest advantage a collection can provide is improved application performance.
Developers utilize collections to 'cache' static data that needs to be regularly accessed. This results in
reduced calls to a database. As I stated earlier, PL/SQL programs are a good place to make expensive SQL
calls but that doesn't mean that we shouldn't try to keep those calls to a minimum.
Oracle uses collections in PL/SQL the same way other languages use arrays. Oracle provides three
basic collections, each with an assortment of methods.
The number 1
The number 2
The number 4
The number 5
VARRAY COLLECTIONS:
A VARRAY is similar to a nested table except you must specify an upper bound in the declaration.
Like nested tables they can be stored in the database, but unlike nested tables individual elements cannot
be deleted so they remain dense:
Varray Collections
-- Traverse collection
v_idx := v_tab.FIRST;
<< display_loop >>
WHILE v_idx IS NOT NULL LOOP
DBMS_OUTPUT.PUT_LINE('The number ' || v_tab(v_idx));
v_idx := v_tab.NEXT(v_idx);
END LOOP display_loop;
END;
/
The number 1
The number 2
The number 3
The number 4
The number 5
INDEX-BY TABLES:
The first type of collection is known as index-by tables. These behave in the same way as arrays
except that have no upper bounds, allowing them to constantly extend. As the name implies, the collection
is indexed using BINARY_INTEGER values, which do not need to be consecutive. The collection is
extended by assigning values to an element using an index value that does not currently exist.
Index-By Table
SET SERVEROUTPUT ON SIZE 1000000
DECLARE
TYPE table_type IS TABLE OF NUMBER(10)
INDEX BY BINARY_INTEGER;
The number 1
The number 2
The number 4
The number 5
COLLECTION METHODS:
A variety of methods exist for collections, but not all are relevant for every collection type:
Examlple#1:
BULKCOLLECT:
BULKCOLLECT#1
BULKCOLLECT#2
More than one function may be defined with the same SQL name, so long as the arguments they
take are different. In other words, function names can be overloaded. When a query is executed, the server
will determine which function to call from the data types and the number of the provided arguments.
Overloading can also be used to simulate functions with a variable number of arguments, up to a finite
maximum number.
You can declare local or packaged stored procedures with exactly the same name, as long as their
parameters are different by at least one of these factors:
SQL> declare
2 function getArea(i_rad NUMBER)
3 return NUMBER
4 is
5 v_pi NUMBER:=3.14;
6 begin
7 return v_pi * (i_rad ** 2);
8 end;
9 function getArea(i_length NUMBER, i_width NUMBER)
10 return NUMBER
11 is
12 begin
13 return i_length * i_width;
14 end;
15 begin
16 DBMS_OUTPUT.put_line('Area (R=3):'||getArea(3));
17 DBMS_OUTPUT.put_line('Area (2x3):'||getArea(2,3));
18 end;
19 /
Area (R=3):28.26
Area (2x3):6
Names Of Parameters
SQL> declare
2 function getArea(i_rad NUMBER, i_prec NUMBER)
SQL> declare
2 function getArea(i_rad NUMBER, i_prec NUMBER) return NUMBER is
3 v_pi NUMBER:=3.14;
4 begin
5 return trunc(v_pi * (i_rad ** 2),i_prec);
6 end;
7 function getArea(i_rad NUMBER, i_ignore_yn VARCHAR2) return NUMBER is
8 v_pi NUMBER:=3.14;
9 begin
10 if i_ignore_yn='Y' and i_rad < 5 then
11 return 0;
12 else
13 return v_pi * (i_rad ** 2);
14 end if;
15 end;
16 begin
17 DBMS_OUTPUT.put_line('Area (R=3):'||getArea(3,1));
18 DBMS_OUTPUT.put_line('Area (R=3):'||getArea(3,'N'));
19 end;
20 /
Area (R=3):28.2
Area (R=3):28.26
SET#1:
1. What is PL/SQL and what is it used for?
SQL is a declarative language that allows database programmers to write a SQL declaration and hand
it to the database for execution. As such, SQL cannot be used to execute procedural code with conditional,
iterative and sequential statements. To overcome this limitation, PL/SQL was created.
PL/SQL is Oracle's Procedural Language extension to SQL. PL/SQL's language syntax, structure and
data types. Some of the statements provided by PL/SQL:
SELECT OBJECT_NAME,
TO_CHAR(CREATED, 'DD-Mon-RR HH24:MI') CREATE_TIME,
TO_CHAR(LAST_DDL_TIME, 'DD-Mon-RR HH24:MI') MOD_TIME,
STATUS
FROM USER_OBJECTS
WHERE LAST_DDL_TIME > '&CHECK_FROM_DATE';
5. How can one search PL/SQL code for a string/ key value?
The following query is handy if you want to know where certain tables, columns and expressions are
referenced in your PL/SQL source code.
set serveroutput on
begin
dbms_output.put_line('Look Ma, I can print from PL/SQL!!!');
end;
begin
EXECUTE IMMEDIATE 'CREATE TABLE X(A DATE)';
end;
begin execute Immediate 'TRUNCATE TABLE emp'; end;
DECLARE
var VARCHAR2(100);
BEGIN
var := 'CREATE TABLE temp1(col1 NUMBER(2))';
EXECUTE IMMEDIATE var;
END;
declare
a number := NULL;
b number := NULL;
begin
if a=b then
dbms_output.put_line('True, NULL = NULL');
elsif a<>b then
dbms_output.put_line('False, NULL <> NULL');
else
dbms_output.put_line('Undefined NULL is neither = nor <> to
NULL');
end if;
end;
14. How does one get the value of a sequence into a PL/SQL variable?
As you might know, one cannot use sequences directly from PL/SQL. Oracle (for some silly reason)
prohibits this:
However, one can use embedded SQL statements to obtain sequence values:
DECLARE
CURSOR dept_cur IS
SELECT deptno
FROM dept
ORDER BY deptno;
END LOOP;
END;
17. How often should one COMMIT in a PL/SQL loop? / What is the best commit strategy?
Contrary to popular belief, one should COMMIT less frequently within a PL/SQL loop to prevent
ORA-1555 (Snapshot too old) errors. The higher the frequency of commit, the sooner the extents in the
undo/ rollback segments will be cleared for new transactions, causing ORA-1555 errors.
18. I can SELECT from SQL*Plus but not from PL/SQL. What is wrong?
PL/SQL respect object privileges given directly to the user, but does not observe privileges given
through roles. The consequence is that a SQL statement can work in SQL*Plus, but will give an error in
PL/SQL. Choose one of the following solutions:
Grant direct access on the tables to your user. Do not use roles!
Another way this error can occur is if the trigger has statements to change the primary, foreign or
unique key columns of the table off which it fires. If you must have triggers on tables that have referential
constraints, the workaround is to enforce the referential integrity through triggers as well.
A row-level trigger cannot query or modify a mutating table. (Of course, NEW and OLD still
can be accessed by the trigger).
A statement-level trigger cannot query or modify a mutating table if the trigger is fired as the
result of a CASCADE delete.
Etc.
As workaround, one can use autonomous transactions. Autonomous transactions execute separate from
the current transaction. Unlike regular triggers, autonomous triggers can contain COMMIT and
ROLLBACK statements.
SET#2
1. What Is PL/SQL Language Case Sensitive?
PL/SQL language is not case sensitive: