Anda di halaman 1dari 207

Introduction to RDBMS

Objectives
In this Chapter, you will learn about RDBMS Concepts. You will learn about
Database Models, Data Integrity and Codds Rule.

Topics

Introduction to RDBMS
DBMS Concepts
RDBMS Terminology
Data Base Models
Data Integrity
Codds Rules

Introduction to RDBMS
RDBMS is the acronym for Relational Database Management System. The
most popular RDBMS packages are ORACLE, SYBASE, INFORMIX and MSSQL SERVER. Before we move on to the RDBMS, it is necessary that we first
understand the concepts of DBMS and how we slowly moved on to the
RDBMS.

Concepts of DBMS
A collection of interrelated data is referred to as a database. A Database
Management System co-ordinates the storage and retrieval of the data and
ensures integrity, consistency and availability. Database systems have been
released that support single user or multi-user systems. The former lets only one
person to access the database at a given time while the latter allows many users
to simultaneously access the database.
To put it in a nutshell, a DBMS offers the following services:
Data definition: This is a method of defining and storing a set of data.
Data maintenance: Takes care to see that each record has fields containing
information about one particular item.
Data manipulation: Allows user to insert, update, delete and sort data in the
database.
Data display: Allows the user to insert, update, delete and sort data in the
database.
Data integrity: Ensures accuracy of the data.

RDBMS Terminology
Entities and Attributes
Let us consider a company as an example. The company necessarily has to store
information about its employees like EMPCODE (Employee Code), NAME
(Employee Name), DEPTNO (Department Number) etc. Each of these is termed
as an entity. Data is stored under each of them. These entities have relationships
between them. For example, an employee may belong to one particular
department. The database stores all the information pertaining to the entities and
their relationships.
An attribute is a characteristic property of an existing entity. It is also necessary
to understand the difference between attribute type and attribute instance. For
example, 'James' is an attribute instance and ENAME is an attribute type. Any
attribute or set of attributes can be used to uniquely identify a row in a database
(table).
Before we start discussing the different data models, let us have a brief look at
the different kinds of relationships.
Relationship among Data
The different relationships recognized among various data stored in the database
are:
One to One
One to Many
Many to Many
One to One relation:
To understand this relationship, consider a set of students in a class. Each
student can have only one roll number and the roll number cannot be duplicated.
One to Many relation
In the above example, let us assume that there is a condition that a student can
do only one course at a time. Now we clearly see that many students have
access to the same course but a student can register in only one particular course
thus showing the one to many relationships.
Many to Many relation
This can be explained by considering the items sold by vendors. A vendor can
sell many items and each item can by sold by many vendors.

Database Models
Organization of a database is complex because apart from just storing data, a
meaningful relationship must be established among them. So it is obvious that
these data should be related to each other. The actual evolution of database
systems took place as shown below:
File Management ----> Hierarchical -----> Network ---> Relational
File Management System (FMS)
The FMS was the first method used to store data in a computerized database.
Here, each field or data item is stored on a disk sequentially in one large file.

The disadvantages of FMS are:

There was no relationship among data other than the sequence in


which it was stored.

A particular record cannot be located easily. To locate a record the


search starts from the beginning and each item is checked
subsequently till the match is found.

It does not allow changes to the database structure easily. For


instance adding a new column to the structure would require the
DBMS to read each record, write it to a temporary file and add the
new information after the last field of each record. After the new file
is written, the original file is deleted and the temporary file is
renamed.

Because of these disadvantages in FMS, the Hierarchical Database System


came into existence.

Hierarchical Database Systems


The basic idea of HDS is to support one to many relationships. In this model,
data structure is in the form of an inverted tree. The origin of the data tree, is
referred to as the root which is unique in HDS. The data structure at each level
is called a node. The last node in the series is called a leaf. If we require any
information, HDS does not search through the entire data structure. Instead, the
search is made only through a particular node. In HDS, the last node is called a
leaf, in which there is a series of pointers from one leaf to another, maintaining
the relationship among the data.
The drawback is, the initial structure need to be defined by the programmer
while creating the database. Also once defined, the tree structure can not be
altered without disturbing the whole structure. This model does not support
many to many relationships. To meet this discrepancy, gradually the Network
Database Systems got evolved.
Network Database Systems
The centralized idea in the NDS is to successfully bring about a many to many
relationship. The relationships between the different data items are commonly
referred to as 'sets'. For example, consider vendors selling various items. If it is
required to know which vendor(s) sell, say item2, the DBMS searches the item
class and follows the pointers from item2 to the vendors who supply them.
Similarly location of item from the vendor class is also possible. Though this
model is very flexible in supporting many to many relationship, when thousands
of items and vendors are involved, the mapping of data could become very
difficult and it will lead to complexity. Once the database is set up, any change
required in the sets require redeveloping the structure.
All the models so far discussed, use pointers to define logical relationships. This
results only in complexity. The idea of 'relationship' led to the design of the
Relational Data Model.

Relational Database Model


The RDM organizes data in logical mathematical sets in a tabular form. Here
each data field is considered as a column and each record is considered as a row
in the table. Taking the vendor(s) details discussed above, they can be grouped
into the tables as follows.
Vendor Details
VNO
V1
V2
V3
V4

VNAME
COMP1
COMP2
COMP3
COMP4

Item Details
INO
I1
I2
I3
I4
I5

Desc
ITEM1
ITEM2
ITEM3
ITEM4
ITEM5
Item Vendor Details

INO
I1
I4
I5
I4
I5

VNO
V2
V4
V1
V2
V1

If one wants to see which are the items sold by COMP2, one just need to join
the two tables using the mathematical JOIN operators. Here we see that any new
change will only involve adding or deleting columns to / from the existing
tables. It is not necessary to build the entire database from the beginning as in
HDS or NDS. Still, we can store the item details in a separate table. The process
of breaking up the data and storing them in tables in order to reduce redundancy
is referred to as normalization.

Data Integrity
This ensures that the data available in the database is always correct and
complete. In order to maintain integrity of data, 'Integrity constraints' are
imposed. Integrity Constraints restrict data values that are inserted or updated in
a database.

Codds Rules
E. F. Ted Codd devised twelve rules, which are to be obeyed by a database for it
to be relational. These rules are discussed below in brief.

Information Representation
All Information is explicitly and logically represented as data values in tables.
From this rule, it is clear that if a data does not exist in a table in the database,
then it is not present at all.

Logical Accessibility
Every item of data must be logically addressable with the help of a table name,
primary key value and column name.

Systematic Treatment of all Null Values


The DBMS must support null values to represent missing or inapplicable
information, which should be independent of data type. NULL is neither space
nor zero.

Catalog Facilities / Database Description Rule


A description of the database is maintained using the same logical structures
with which data was defined by the DBMS. These are accessible by users with
appropriate authority and are stored in the data dictionary.

Comprehensive Data Language Rule


According to this rule the system must support the following:
Data definition
View definition
Data manipulation
Integrity Constraints
Authorization
Transaction management operators

View Updating Rule


All views that are updateable by theory can also be updated by the system.

High-Level Insert and Update Rule


A single operand must hold good for all the retrieve, update, delete and insert
activity. This rule implies that all the data manipulation commands must be
operational on sets of rows rather than on a single row.

Physical Data Independence Rule


User's access to database must be consistent irrespective of the changes in
storage representation or access methods to data.

Logical Data Independence Rule


Application programs and terminal activities should remain logically unaffected
when the design of the database is changed. The change can be splitting the
table into many fragments, i.e., dividing it into more tables.

Integrity Independence Rule


Integrity constraints should be stored in the database as data in tables.

Distribution Independence Rule


Distribution independence rule must be available in the RDBMS. If the data in
the database becomes distributed, applications running on the database should
not be hindered.

Non-subversion Rule
If an RDBMS supports a lower level language then it should not bypass any
integrity constraints defined in the higher level.

Introduction to SQL*PLUS and DDL


Commands
Objectives
In this Chapter, you will have an introduction to SQL and SQL*PLUS and learn about
the CREATE TABLE, the DESC, the ALTER TABLE, the DROP TABLE, the
GRANT PRIVILEGE and the REVOKE PRIVILEGE commands.

Topics

Introduction
SQL and SQL*Plus
The CREATE Command
The DESC Command
Data Types In Oracle
Integrity Constraints
The ALTER Command
The DROP TABLE Command
The GRANT PRIVILEGE Command
The REVOKE PRIVILEGE Command

Introduction to SQL*Plus
The name SQL pronounced as 'ess-cue-ell' or 'sequel' is the abbreviation for
Structured Query Language. SQL consists of a set of facilities for defining,
accessing and managing relational databases such as ORACLE, MS-SQL,
SYSBASE, etc,.
The advantages of SQL are:

SQL is extremely flexible. It uses a free form syntax that gives the
user the ability to structure SQL statements in a way best suited to
him.

Applications written in SQL can be easily ported across systems.

SQL is not merely a query language. The same language can be used
to define data structures, control access to the data and delete, insert
and modify occurrences of the data.

The language even though is simple and easy to learn, can handle
complex situations.

Throughout its life cycle, SQL received natural extensions to its functional
capabilities and what was originally intended as a query language has now
become the complete Database Language.

SQL and SQL*Plus


SQL*PLUS is an Oracle server tool that recognizes and executes SQL
statements. It is one of the most common ways to communicate interactively
with the Oracle database. One of the benefits of SQL*PLUS is that you can edit
or save the SQL statements that are in the SQL buffer.
The SQL buffer is a part of the memory managed by SQL*PLUS that stores one
SQL command at a time. A single SQL command remains in the SQL buffer
until a new command is issued.

Types of SQL Commands


Based on their functionality, SQL commands can be classified as follows.
Data Definition Language (DDL), which is used to define the database objects
with CREATE, ALTER, DROP commands.
Data Manipulation Language (DML), which is used to access and modify the
data with SELECT, INSERT, DELETE and UPDATE commands.
Transaction Control Language (TCL), which is used to manage all the
changes made by the DML commands.
In addition to this, there are GRANT and REVOKE commands, which are used
to share the database objects between users.

The CREATE Command


A table in a relational system consists of row of column headings, together with
zero or more rows of data values. The CREATE TABLE command creates a
table.
Syntax: CREATE TABLE tablename (columnname datatype(size), columnname
datatype(size),....);
The restrictions in giving tablename are:
The table name should start with an alphabet and it should not contain any
special characters except '_' and digits [0-9].
It should not contain spaces.
It should not be an Oracle reserved word.
It should not be duplicated with an already existing table.
It is not case sensitive. The tablenames Emp, eMp, EMP, emp refer to the same
table.
But, tablenames within double quotations are case sensitive. For example:
"Emp" and "eMp" refer to two different tables. They can contain any special
characters except double quotations.
Note: A comma delimits one parameter from another. A semi colon indicates
the end of an SQL sentence.
To create a table by name dept, enter the following command:
SQL> CREATE TABLE dept (deptno number(2) primary key, dname
varchar2(20) not null, location varchar2(20));
After this command is executed successfully you will get the message 'Table created' which tells you
that the table has become a part of your Oracle database.

Note: In the above table definition the column deptno has been defined as the
primary key which means that the value for that column can neither be
duplicated nor be null. It is the row identifying the column. Also note that the
column dname has been defined as not null which forces the user to enter a
value for that column (explained later in this chapter).

The DESC Command


To view the structure of a table issue the Desc (describe) command
Syntax: DESC {object_name}
For example, the command
SQL> DESC dept
Gives the information about all the columns of dept table, their data types and
whether they are null-able or not.

Data Types in Oracle


Each literal or column value manipulated by ORACLE has a datatype. A value's
datatype associates a fixed set of properties with the value. These properties
cause ORACLE to treat values of one datatype differently from values of
another. When you create a table, you must specify an internal datatype for each
of its columns. These datatypes define the domain of values that each column
can contain or each argument can have. Table below summarizes ORACLE
internal datatypes.

Data type
Varchar2(size)

Description
Variable length character string having maximum length
size bytes. Maximum size is 2000. You must specify the
size.

Number(p,s)

Number having precision 'p' and 's' scales. The precision p


can range from 1 to 38. The scale s can range from 84 to
127.
Character data of variable length up to 2 GB or 2 power
31 -1.
Raw binary data of length size bytes. Maximum is 255.
Raw binary data of variable length up to 2 GB.
Hexadecimal string representing the unique address of a
row in its table.
Fixed length character data of length size bytes.
Maximum size is 255. Default size is 1 byte.
A valid date range from Jan 1, 4712 BC to Dec 31, 4712
AD.

Long
Raw (size)
Long Raw
Rowid
Char(size)
Date

Examples of Column width specifications and their meanings:


Char(12)

column may contain char values up to 12 characters long.

Number

column may contain number values up to 38 digits long.

Number(4)

column may contain number values up to 4 digits long.

Number(8,3) column may contain number values up to 8 digits long, 3 of


which are allocated for decimal places.
Date

column may contain date values.

Integrity Constraints
ORACLE provides automatic ways to ensure data integrity. We can declare
integrity constraints at table definition level. The constraints declared
automatically validate data against correction. To define an integrity constraint,
include a CONSTRAINT clause in a CREATE or ALTER table command (as
we did while creating dept table).
NOT NULL Constraints:
The NOT NULL constraint specifies that a column cannot contain null values.
To satisfy this constraint, every row in the table must contain a value for the
column. The NULL keyword indicates that a column can contain nulls.
Example: This statement creates the dept table with dname defined as not null.
SQL> CREATE TABLE dept (deptno number(2) primary key, dname
varchar2(20) NOT NULL, location varchar2(20));
OR
SQL> CREATE TABLE dept (deptno number(2) ,dname varchar2(20)
CONSTRAINT NN_DNAME NOT NULL, location varchar2(20));
Note that in the second option we have given a name for the constraint using the
CONSTRAINT clause.

Unique Constraint
The UNIQUE constraint designates a column or combination of columns as a
unique key. To satisfy this, no two rows in the table can have the same value for
the unique key. However, the unique key made up of a single column can
contain nulls. A unique key column cannot be of datatype LONG or LONG
RAW. You cannot designate the same column or combination of columns as
both a unique key and a primary key. However, you can designate the same
column or combination of columns as both a unique key and a foreign key. We
can also define composite unique keys, made up of combination of columns. In
that case a maximum of 16 columns are allowed.
Example: The following statement creates the dept table and defines the dname
to be unique.
SQL> CREATE TABLE dept (deptno number(2), dname varchar2(20)
CONSTRAINT unq_dname UNIQUE, location varchar2(20));
This constraint ensures that no two departments have the same name. But the
department name can be Null.

Primary Key Constraint


A Primary Key constraint designates a column or combination of columns as
the table's primary key. To satisfy this constraint, no two rows in the table can
have the same value for the primary key, and no column that is a part of primary
key can be Null. A table can have only one primary key. A primary key column
cannot be of datatype LONG or LONG RAW. You cannot designate the same
column or combination of columns as both a primary key and a unique key.
However, you can designate the same columns or combination of columns as a
primary key and a foreign key. We can also define a composite primary key that
is made up of a combination of columns. In that case a maximum of 16 columns
are allowed.

Example: This example defines the deptno of the dept table as the primary key.
SQL> CREATE TABLE dept (deptno number(2) CONSTRAINT dept_key
PRIMARY KEY, dname varchar2(20) ,location varchar2(20));
The above constraint ensures that deptno may not be duplicated and left blank.

Referential Integrity Constraints


A Referential Integrity constraint designates a column or combination of
columns as a foreign key and establishes a relationship between that foreign key
and a specified primary or unique key, called the referenced key. In this
relationship, the table containing the foreign key is called the child table and the
table containing the referenced key is called the parent table. To satisfy this
constraint, each row of the child table is said to depend on the referenced key in
the parent table.
Example: The following statement creates the emp table and defines a foreign
key on the deptno column of the dept table.
SQL> CREATE TABLE emp (empno number(4) primary key, ename
varchar2(20) not null, job varchar2(10), mgr number(4), hirdate date, sal
number(7,2), comm number(7,2), deptno number(2) CONSTRAINT fk_deptno
REFERENCES dept(deptno));
The above constraint ensures that all employees in the emp table work in a
department in the dept table. However, employees can have null dept numbers.
Before you enable this constraint, it is necessary that you should have defined
the deptno column of the dept table as the primary key or unique key.

Using the ON DELETE CASCADE option


If you use the ON DELETE CASCADE option, ORACLE permits deletions of
referenced key values in the parent table and automatically deletes dependent
rows in the child table.
Example: This example creates the emp table, defines the referential integrity
constraint with ON DELETE CASCADE option:
SQL> CREATE TABLE emp (empno number(4) primary key, ename
varchar2(20) not null, job varchar2(10), mgr number(4), hirdate date, sal
number(7,2), comm number(7,2), deptno number(2) CONSTRAINT fk_deptno
REFERENCES dept(deptno) ON DELETE CASCADE);

Check Constraint
The CHECK constraint explicitly defines a condition. To satisfy this constraint,
each row in the table must make either TRUE or unknown (due to a null). The
condition of a CHECK constraint can refer to any column in the table, but it
cannot refer to columns of other tables.
Example: The following example checks the salary of the employee to be
positive.
SQL> CREATE TABLE emp (empno number(4) primary key, ename
varchar2(20) not null, job varchar2(10), mgr number(4), hirdate date, sal
number(7,2) CONSTRAINT chk_sal CHECK ( sal > 0), comm number(7,2),
deptno number(2) CONSTRATIN fk_deptno REFERENCES dept(deptno));

The Alter Command


The Alter Table command can be used to:

Add a new column to a table


Modify the definition of existing columns
Add constraint to a table
Drop a constraint

Suppose we want to increase the width of the salary column of the emp table to
number (8,2), For that enter,
SQL > ALTER TABLE emp MODIFY (sal NUMBER(8,2));
You will get the message 'Table Altered'. So the salary column now is defined
as number (8,2).
Using this command, you can decrease the column's width or change its data
type only if there are no non-null values in the column.
If you want to add a new column, say, age column to the emp table, enter:
SQL> ALTER TABLE emp ADD (age NUMBER(2) CONSTRAINT age_chk
CHECK (age between 21 and 58));
Note that age has been explicitly checked with a check constraint, which tells
you that you can include a constraint clause in the Alter Table command.
However, for a new column, which is added through ALTER TABLE command
we can include the NOT NULL constraint, only if the tables contains no rows.

The following example adds a primary key constraint to the deptno of the dept
table (if it is not already defined as primary key).
SQL> ALTER TABLE dept ADD PRIMARY KEY(deptno);
Points to Ponder
With the Alter Table command one can not do the following tasks:

Renaming a column.
Removing a column from the table.
Decreasing the size of a column when the table contains row(s).
Defining the newly added column as NOT NULL when the table
contains row(s).

The Drop Table Command


To remove the table from the database, use the DROP TABLE command.
Syntax: DROP TABLE {table_name};
For example, the command
SQL> DROP TABLE emp;
Removes the emp table from the database. It is wise to use this command once
you are sure of removing the table.

The GRANT PRIVILEGE Command


One owns the table that he has created using CREATE TABLE command. If he
wants to share such an object with other ORACLE users, GRANT command
should be issued.
Syntax:
GRANT
OPTION].

{privileges} ON

{object} TO

{user} [WITH GRANT

The privileges that can be granted on a table are: SELECT, INSERT, UPDATE,
DELETE, ALTER and INDEX.
Example: To grant MIKE the privilege only to SELECT from your table
DEPT, enter:
SQL>GRANT SELECT ON DEPT TO MIKE;
Grant succeeded.
To grant several privileges at once, enter all the privileges, separated by
commas. Similarly to grant the privileges to more than one user, enter all the
users separated by commas. When you grant an access privilege, the user who
receives the grant normally does not receive the authority to pass the privilege
on to others. To give a user authority to pass privileges on, use the option clause
WITH GRANT OPTION.
Example: To grant the SELECT privilege on EMP to MIKE, with authority to
grant that privilege to others, enter:
SQL> GRANT SELECT ON EMP TO MIKE WITH GRANT OPTION;
Grant succeeded.

The REVOKE PRIVILEGE Command


To withdraw a privilege you have granted, use the REVOKE command. It is
just opposite to the GRANT command.
Syntax: REVOKE {privileges} ON {object} FROM {user(s)};
When you use this command, the privileges you specify are revoked from the
users you name, and from any other users to whom they have granted those
privileges. To revoke all privileges on DEPT from ADAMS, enter:
SQL> REVOKE ALL ON DEPT FROM ADAMS;
Revoke succeeded.

Data Manipulation Commands


Objectives
In this Chapter, you will learn about Data Manipulation Commands like THE INSERT,
THE SELECT, THE UPDATE and THE DELETE COMMAND.

Topics

The INSERT COMMAND


Copying Rows between Tables
The SELECT Command
The UPDATE Command
The DELETE Command

Introduction
INSERT, DELETE, UPDATE and SELECT are the Data Manipulation
Commands.

The INSERT Command


The INSERT command is used to insert a row into a table.
Syntax: INSERT INTO {table_name} VALUES (a list of data values separated
by comma);
Example: To insert a new row into the EMP table enter:
SQL > INSERT INTO EMP VALUES (7965,'PETER','CLERK',7865,'08-JUN90',3200,200,30);
1 row created.
When adding records with this command, the values must be in the same order
as the columns were defined when the table was created. In the above example,
the value 7965 corresponds to Empno and 'PETER' corresponds to Ename of
Emp table and so on. The char and date values are enclosed within quotes.
Inserting Null Values:
If you want to insert a null value into a field, say, COMM column, use the
NULL keyword (not enclosed within quotes).
Example: To insert a new row into the EMP table with NULL commission
enter:
SQL > INSERT INTO EMP VALUES (7952,'KRIS','CLERK',7865,'08-JUN90',3250,NULL,30);
If you want to place null values in several columns, there is a shortcut method.
Instead of specifying NULL for each blank column, list only the columns and
values you want to enter as given in the following example.

Example: To add values in the selected columns only, enter:


SQL> INSERT INTO EMP (EMPNO,ENAME,HIREDATE,DEPTNO,SAL)
VALUES(7123,'JOHN', '23-JAN-91',30,4000);
You need not enter the column names in the same order as they appear in the
table, but you must enter the values in the same order as the column names.
Note that the columns, which do not appear in the insert command, should not
have been defined as NOTNULL. Otherwise, ORACLE will raise an error
message and will not insert the row.

Copying Rows between Tables


You can use the insert command with a query to select rows from one table and
insert them into another table. The query replaces the values clause. For
example, suppose you want to give bonus to all the managers in the company,
along with all other employees whose commission is greater than 25% of their
salary, you must copy the records of these employees from EMP to BONUS
table.
Example: To copy rows of the EMP table into the BONUS table, enter:
SQL> INSERT INTO BONUS (ENAME,JOB,SAL,COMM) SELECT
ENAME,JOB,SAL,COMM FROM EMP WHERE JOB='MANAGER' OR
COMM>0.25 * SAL;

The SELECT Command


A query is a request for information, and querying is one of the most common
database operations.
Queries are performed using the SELECT command.
Syntax: SELECT {column_name1, column_name2,}....FROM {table1,table2,}
....;
A select command must have at least two clauses.
1. SELECT the columns clause.
2. FROM table(s) clause which contain those columns.
For example, the command
SQL > SELECT ename FROM emp;
Instructs the SQL*PLUS to display all the names of the employees from the
emp table.
You can display all the columns of a table or only specific columns. For
example, to select just the columns DNAME and DEPTNO from the table dept,
enter:
SQL> SELECT DNAME,DEPTNO FROM DEPT;
To select all the columns of a table, you need not list the names of all the
columns in the select command. You can use the ' * ' character.

Example: To display all the columns of the emp table, enter:


SQL> SELECT * FROM EMP;
Unless you indicate, SQL*PLUS displays the results of a query without
eliminating duplicate entries. For example, if you want to list all jobs from the
company, you will have to enter:
SQL> SELECT JOB FROM EMP;
This displays the list of all jobs, but some job types are listed more than once, as
more than one employee is doing the same job. To avoid such duplication, use
the DISTINCT clause as shown below.
SQL> SELECT DISTINCT(JOB) FROM EMP;

The WHERE clause


The WHERE clause is used to select only specific type of rows.
Syntax: SELECT columns FROM table WHERE condition;
For example, if one wants to see the information about dept 30 employees only,
then one has to enter:
SQL> SELECT * FROM EMP WHERE DEPTNO=30;
The table below shows the comparison operators that can be used in the
WHERE clause.
Operator

Meaning

=
! = or <>
>
>=
<
<=
Between
In(list)
LIKE
IS NULL

equal to
not equal to
greater than
greater than or equal to
less than
less than or equal to
between any two values
any of a list of values.
match a string pattern
is a null value

To negate the last four operators, use the operators NOT BETWEEN, NOT IN,
NOT LIKE, and IS NOTNULL.

Example: To find those employee whose commission is greater than their


salary, enter the following:
SQL> SELECT EMPNO,ENAME FROM EMP WHERE COMM > SAL;
Suppose you want to find all the sales people in dept 30 whose salary is greater
than equal to $ 1500, enter,
SQL > SELECT ENAME, SAL, DEPTNO FROM
JOB='SALESMAN' AND DEPTNO=30 AND SAL >=1500;

EMP

WHERE

Here, we have connected the logical expressions by means of the AND


operator. AND means that all the component expressions must be true for the
query to satisfy the criteria.
Similarly we can also use OR operators. We can select the rows, which satisfy
at least one of the component expressions connected by the OR operators.

Example: To list names, job, salary of employees whose job is manager or


salary is greater than or equal to $3000 , enter:
SQL> SELECT ENAME, JOB, SAL FROM EMP WHERE JOB='MANAGER'
OR SAL >=3000;

Negating expressions
The expressions can be negated with a NOT operator. For example, to list the
information about all employees in dept10 who are not managers or clerks,
enter:
SQL> SELECT * FROM EMP WHERE NOT (JOB='MANAGER' OR
JOB='CLERK') AND DEPTNO=10;
The BETWEEN operator lets you select rows in which a column contains a
value within a range.
Example: To get the list of employees, whose salary is between $ 2500 and $
4000, enter:
SQL> SELECT ENAME, JOB, SAL FROM EMP WHERE SAL BETWEEN 2500
AND 4000;
The IN operator lets you select rows, which match one of the values in a list.
For example, to find the employees who are clerks, analysts or salesmen, enter:
SQL> SELECT ENAME, JOB, DEPTNO FROM EMP WHERE JOB IN
('CLERK','ANALYST', 'SALESMAN');

Similarly you can use NOT IN operator to negate the above example.
When you search for a particular character pattern, say, ename starting with the
alphabet 'S' or Job containing the letter 'R', you can use the LIKE operator. The
LIKE operator is associated with two special characters '%' and '_'. The %
character replaces a set of characters where the _ character replaces a single
character.
Example: To find the jobs and departments of employees, whose names begin
with M, enter:
SQL> SELECT ENAME, JOB, DEPTNO FROM EMP WHERE ENAME LIKE
'M%';
The % sign after the letter M, tells the SQL*PLUS to select the names starting
with letter M, regardless of how many characters follow.

Example: To list the jobs and salaries of employees, whose name begin with
the ALL and end with N and five characters in length, enter:
SQL> SELECT JOB, SAL FROM EMP WHERE ENAME LIKE 'ALL_N';
As it is obvious from the above example, _ replaces a single character.
We can use the IS NULL operator to check for null values.
Example: To list the employees, who are not eligible to receive a commission,
enter:
SQL> SELECT EMPNO, NAME FROM EMP WHERE COMM IS NULL;

Controlling the Order of Displayed Rows


One can control the order in which rows are displayed by adding the ORDER
BY clause to a SELECT statement. Using this clause, we can order the rows in
an ascending order or descending order with respect to a column.
Example: To list employees and jobs in Department 30 in descending order by
salary enter:
SQL > SELECT SAL, JOB, ENAME FROM EMP WHERE DEPTNO=30
ORDER BY SAL DESC;
If one wants the rows in the ascending order with respect to a particular column,
then just the word 'order by' is enough.
Example: To list the employees and jobs in Department 30 in the ascending
order of salary, enter:
SQL> SELECT SAL, JOB, ENAME FROM EMP WHERE DEPTNO=30
ORDER BY SAL;

The UPDATE Command


The UPDATE command is used to change the values of existing rows in the
table. The UPDATE command consists of an UPDATE clause followed by SET
clause and an optional WHERE clause.
Syntax: UPDATE {table} SET {column = value, column = value,} .... [WHERE
condition];
Suppose ROBERT one of the employees you inserted into EMP table, is
assigned to the sales staff and given a 10% raise in salary. This can be done
using,
SQL> UPDATE EMP SET
JOB='SALESMAN',HIREDATE=SYSDATE,SAL=1.1*SAL WHERE
ENAME='ROBERT';
The WHERE clause in the UPDATE command may also contain a query.
Suppose every employee whose name appears in the BONUS table, is rewarded
with a 5% raise. To accomplish the above, enter:
SQL> UPDATE EMP SET SAL=SAL*1.05 WHERE ENAME IN (SELECT
ENAME FROM BONUS);
To confirm the update, enter:
SQL> SELECT * FROM EMP WHERE ENAME IN (SELECT ENAME FROM
BONUS);
The SET clause of the UPDATE command may also contain a query. Such
query must return exactly one row, and must return the same number and type
of columns as the columns being updated.
Example: To set salaries of all salesmen equal to 1.1 times the average salary
of salesmen, enter:
SQL> UPDATE EMP SET SAL=(SELECT 1.1*AVG(SAL) FROM EMP
WHERE JOB='SALESMAN');

The DELETE Command


The DELETE command contains a FROM clause followed by an optional
WHERE clause.
Syntax: DELETE FROM {table} [WHERE condition];
GANESH is no longer eligible for bonuses. Use DELETE command to delete
him from the BONUS table.
SQL> DELETE FROM BONUS WHERE ENAME='GEORGE';
To DELETE all the rows from the table use the delete command without the
where clause.
The command needed here is:
SQL> DELETE FROM BONUS;
Deletes all the rows in the bonus table.
The WHERE clause of the DELETE command may also contain a query.
Example: To delete all the employees with the same job as LUCY from the
BONUS table, enter:
SQL> DELETE FROM BONUS WHERE JOB IN (SELECT JOB FROM EMP
WHERE ENAME='LUCY');

LAB: Creating Tables and Inserting Records


Objectives
In this session, you will create 3 tables (Author, Book and Studies) for a
Publishing Company and insert data into the tables.

Topics

Create the AUTHOR Table


Create the BOOK Table
Create the STUDIES Table
Insert records in the AUTHOR Table
Insert records in the BOOK Table
Insert records in the STUDIES Table
Solutions

1. Create the following Table:


Table Name:

AUTHOR

Name

Null?

Type

NAME
DOB

NOT NULL

VARCHAR2(20)
DATE

DOJ
SEX
LANG1
LANG2
SALARY

DATE
CHAR(1)
VARCHAR2(20)
VARCHAR2(20)
NUMBER(7,2)

NAME is the name of the author.


DOB is the date of birth of the author.
DOJ is the authors date of joining the Publishing Company.
SEX is the sex of the author.
LANG1 is the language in which the author is most fluent.
LANG2 is the second language known to the author.
SALARY is the salary drawn by the author from the Publishing Company.

2. Create the following Table:


Table Name:

BOOK

Name

Null?

Type

NAME
TITLE

NOT NULL

VARCHAR2(20)
VARCHAR2(25)

WRI_IN
BCOST
WCOST
SOLD

VARCHAR2(20)
NUMBER(7,2)
NUMBER(7,2)
NUMBER(3)

NAME is the name of the author writing a book.


TITLE is the title of the book, written by the author.
WRI_IN is the language in which the book is written.
BCOST is the book selling cost.
WCOST is the writing cost or the amount spent in writing the book.
SOLD is the number of copies sold.

3. Create the following Table:


Table Name:

STUDIES

Name

Null?

Type

NAME
UNIVER

NOT NULL

VARCHAR2(20)
VARCHAR2(20)

COURSE
CCOST

VARCHAR2(20)
NUMBER(6)

NAME is the name of the author who underwent the course.


UNIVER is the name of the University where the author underwent his/her course.
COURSE is the Course undergone by the author in a University.
CCOST is the Course Fee Cost.

4. Insert the following data in the table AUTHOR:


NAME
RANDY
DANIEL
SOLOMON
ROSY
CATHARINE
DIANA
BRAIN
LUKE
STEWART
STEPHEN
ELIZABETH
ANITA
LUCILLE
MAUREEN

DOB
12-APR-66
19-MAY-70
10-OCT-70
25-JAN-75
22-OCT-73
30-JUN-74
26-SEP-70
30-NOV-65
28-AUG-65
20-JUL-72
03-JAN-75
30-APR-74
02-DEC-69
03-DEC-75

DOJ
12-APR-94
21-MAR-92
10-OCT-94
16-SEP-97
05-JAN-95
06-AUG-96
04-JUL-93
11-APR-90
19-APR-93
18-SEP-94
05-APR-98
23-OCT-97
02-FEB-94
04-NOV-96

S
M
M
M
F
F
F
M
M
M
M
F
F
F
F

LANG1
TAMIL
ENGLISH
HINDI
LATIN
JAPANESE
GREEK
LATIN
TAMIL
ARABIC
TAMIL
URUDU
JAPANESE
TAMIL
FRENCH

LANG2
URUDU
TELGU
GERMAN
SPANISH
SPANISH
HINDI
SPANISH
ENGLISH
JAPANESE
SPANISH
LATIN
ARABIC
URUDU
JAPANESE

SALARY
3800
2900
4400
3100
3000
5000
2500
2900
3100
3800
2500
3100
3500
5000

5. Insert the following data in the table BOOK.


NAME

TITLE

WRI_IN

BCOST

WCOST

SOLD

RANDY

GENERAL KNOWLEDGE

URUDU

450

250

60

RANDY
SOLOMON
SOLOMON
ROSY
CATHARINE
DIANA
DIANA
DIANA
LUKE
STEWART
STEWART
STEPHEN
STEPHEN
ANITA
ANITA
LUCILLE
LUCILLE

ACCOUNTING POLICY
SHORT STORIES
KNOW YOUR ENGLISH
JAPANESE IN 30 DAYS
KNOW YOUR SALES TAX
BANKING
LEARN ARCHITECTURE
ACCOUNTING POLICY
STATISTICS
EXCISE POLICY
CURRENT COMPUTERS
PROGRAMMING IN C++
GRE ENTRANCE EXAMS
INTERIOR DECORATION
SELF COOKING
DO IT YOURSELF
PERSONALITY
EVALUATOR
BEAUTY TIPS

TAMIL
GERMAN
HINDI
LATIN
SPANISH
HINDI
GREEK
GREEK
TAMIL
ARABIC
JAPANESE
SPANISH
TAMIL
JAPANESE
ARABIC
TAMIL
URUDU

350
650
300
250
200
250
500
450
350
600
500
500
550
750
90
125
150

200
400
100
125
100
150
225
250
200
450
300
250
300
400
40
80
80

40
35
40
25
15
25
20
45
30
30
45
35
45
50
80
20
30

JAPANESE

200

120

40

MAUREEN

6. Insert the following data in the table STUDIES.


NAME

UNIVER

COURSE

CCOST

RANDY
DANIEL
SOLOMON
ROSY
CATHARINE
DIANA
BRAIN
LUKE
STEWART
STEPHEN
ELIZABETH
ANITA
LUCILLE
MAUREEN

OXFORD
CAMBRIDGE
FLORIDA
BOMBAY
HARWARD
OXFORD
HARWARD
HARWARD
ALASKA
OXFORD
CALIFORNIA
SYDNEY
OXFORD
SYDNEY

M.SC
B.COM
B.COM
B.COM
M.COM
M.SC
M.E
B.A
M.A
M.SC
B.SC
B.E
M.E
B.COM

40000
15000
12000
15000
35000
40000
75000
10000
30000
40000
11000
50000
60000
14000

SOLUTIONS
SOLUTION 1
SQL> CREATE TABLE AUTHOR (NAME VARCHAR2(20) NOT NULL,
DOB DATE,DOJ DATE,SEX CHAR, LANG1 VARCHAR2(20), LANG2
VARCHAR2(20), SALARY NUMBER(7,2));
SOLUTION 2
SQL> CREATE TABLE BOOK (NAME VARCHAR2(20) NOT NULL, TITLE
VARCHAR2(25), WRI_IN VARCHAR2(20), BCOST NUMBER(7,2), WCOST
NUMBER(7,2),SOLD NUMBER(3));
SOLUTION 3
SQL> CREATE TABLE STUDIES (NAME VARCHAR2(20) NOT NULL, UNIVER
VARCHAR2(20), COURSE VARCHAR2(20),CCOST NUMBER(6));
SOLUTION 4
Insert the first record using the following command.
SQL> INSERT INTO AUTHOR VALUES('RANDY','12-APR-66','12-APR94','M','TAMIL', 'URUDU',3800);
Similarly insert the rest of the records.
SOLUTION 5
Insert the first record using the following command.
SQL> INSERT INTO BOOK VALUES ('RANDY', 'GENERAL KNOWLEDGE',
'URUDU', 450, 250, 60);
Similarly insert the rest of the records.
SOLUTION 6
Insert the first record using the following command.
SQL> INSERT INTO STUDIES VALUES ('RANDY', 'OXFORD', 'M.SC',
40000);
Similarly insert the rest of the records

Joins and Sub Queries


Objectives
In this session, you will learn about Joins, Equi-Joins, Non-Equi-Joins, Outer Joins, and
Subqueries.

Topics

Joins
Equi-Joins and Non-Equi-Joins
Outer Joins
Subqueries
Subqueries returning set of values
Multiple Subqueries
Correlated Subqueries

JOINS
Rows in one table may be joined to Rows in another table by common values in
corresponding columns. For example, the sample tables EMP and DEPT both
have a column DEPTNO, which contain department numbers. These columns
allow you to join rows in the two tables. To make a query, in which rows of two
tables are joined, you must specify the join columns that contain corresponding
information in the two tables. Specify the tables you use in the FROM clause of
the query and specify the JOIN condition in the WHERE clause.
Format: SELECT columns FROM table1,table2,... WHERE [join condition];
For example, if you want to find the location of ROBERT, you have to join the
two table emp and dept as shown below:
SQL> SELECT ENAME,LOC FROM EMP,DEPT WHERE ENAME='ROBERT'
AND EMP.DEPTNO = DEPT.DEPTNO;
Here, the second logical expression EMP.DEPTNO = DEPT.DEPTNO is the
join condition, which specifies that if the value of deptno in a row in EMP is
equal to the value of DEPTNO in a row in DEPT, those rows are to be joined.
As the EMP and DEPT tables have a column named DEPTNO, we are prefixing
the column with the table name. However, if a column is unique in query, you
need not prefix it as we did not prefix for LOC column, which appears only in
DEPT table.

Abbreviating the Table name


Although table name prefixes prevent ambiguity in a query, they can be tedious
to enter. You can define temporary labels in the FROM clause and use them
elsewhere in the query. Such temporary labels are sometimes called aliases. For
example, To list the employees working in London, enter:
SQL> SELECT D.*,ENAME,JOB FROM EMP E , DEPT D WHERE
E.DEPTNO=D.DEPTNO AND D.LOC='London';
In this example, we have used the aliases E and D for EMP and DEPT tables
respectively.

EQUI-JOINS and NON-EQUI-JOINS


When you join DEPT to EMP table, the join condition specifies the relationship
between them. The type of join you used in the exercise is called an equi-join,
because the comparison operator in the join condition is '='. A join condition
may specify any relationship between columns, not just ' ='. A join condition
that specifies a relationship other than ' =' is called a non-equi-join.

Example: To find the salary and job of those who earn more than JONES,
enter:
SQL> SELECT X.ENAME,X.SAL,X.JOB, Y.ENAME,Y.SAL,Y.JOB FROM EMP
X , EMP Y WHERE X.SAL> Y.SAL AND Y.ENAME='JONES';
Note that in the above example, EMP table has been logically split into two
tables, with alias names X and Y, and rows in X are joined to that of Y, using a
non-equi-join. Since the table is joined to itself, it is also a kind of self-join.

OUTER JOINS
If a row in one of the tables does not satisfy the join condition, that row
ordinarily will not appear in the query result. If you want to display those
department rows that have no matching employees, use the outer join operator,
a plus sign enclosed in parentheses, (+).
Example: To join EMP and DEPT and list dept 30 and 40 with or without
employees, enter:
SQL> SELECT DEPT.DEPTNO, DNAME, JOB, ENAME FROM DEPT.EMP
WHERE DEPT.DEPTNO=EMP.DEPTNO(+) AND DEPT.DEPTNO IN(30,40)
ORDER BY DEPT.DEPTNO;
The above statement gets all the details of dept, even though there is no
employee in departments 30 or 40.

SUBQUERIES
Subqueries are most often used in the WHERE clause of a SELECT command.
Subqueries may be used in several other clauses and commands as well. They
are useful when you want to select rows from a table with a condition that
depends on a data in the table itself.
Example: To find all the employees with the same job as JONES, enter:
SQL> SELECT ENAME, JOB FROM EMP WHERE JOB=(SELECT JOB
FROM EMP WHERE ENAME='JONES');
The above example shows the most basic use of a subquery, which returns a
single value. SQL*PLUS evaluates the innermost query and returns the JOB of
JONES, which in turn is compared with the job of the main query. Subqueries
can be used in any command's WHERE clause. Commands which accept
WHERE clause, are SELECT, UPDATE, INSERT and CREATE.

Subqueries returning set of values


Some subqueries may return more than one value. In that case, you must specify
how the returned values should be used in the WHERE clause of the main
query. For that, we can use the ANY and ALL operators.
Example: To display information about employees, who earn more than any
employee in Dept 30, enter:
SQL> SELECT SAL, JOB, ENAME, DEPTNO FROM EMP WHERE SAL>
ANY(SELECT SAL FROM EMP WHERE DEPTNO=30) ORDER BY SAL
DESC;
The main query returns all the employees who earn more than the lowest salary
in dept 30.
If you use ALL after the comparison operator, the query will select the rows in
which salary is greater than the highest salary returned by the subquery.
Example: To display information about employees, who earn more than all the
employees in dept 30, enter:
SQL> SELECT SAL, JOB, ENAME, DEPTNO FROM EMP WHERE SAL>
ALL(SELECT SAL FROM EMP WHERE DEPTNO=30) ORDER BY SAL
DESC;

Multiple Subqueries
The WHERE clause of the main query may contain any combination of
ordinary conditions and subqueries. In particular, it may contain any number of
conditions with subqueries, connected by the operators AND or OR.
Example: To list the employees with either the same job as JONES or a salary
greater than or equal to FORD'S, enter:
SQL> SELECT ENAME, JOB, DEPTNO, SAL FROM EMP WHERE
JOB=(SELECT JOB FROM EMP WHERE ENAME='JONES') OR
SAL>=(SELECT SAL FROM EMP WHERE ENAME='FORD') ORDER BY
JOB, SAL;
A query may be composed of two or more queries with the operators UNION
and INTERSECTION.
Union returns all distinct rows returned by either of the queries it applies to.
Intersection returns all rows returned by both of the queries it applies to.
Example: To list employees whose salary is equal to that of SCOTT or WARD,
enter:
SQL> SELECT ENAME, JOB, SAL FROM EMP WHERE SAL IN(SELECT
SAL FROM EMP WHERE ENAME='SCOTT' UNION SELECT SAL FROM
EMP WHERE ENAME='WARD');
A subquery can retrieve information from more than one table.
Example: To list the employees having the same jobs as employees located in
London, enter:
SQL> SELECT ENAME, JOB FROM EMP WHERE JOB IN(SELECT JOB
FROM EMP,DEPT WHERE LOC='London' AND
EMP.DEPTNO=DEPT.DEPTNO);

Correlated Subqueries
In the above examples, a subquery was executed once, and the resulting value
was used by the main query only once. In certain cases, subquery is executed
repeatedly once for the each row returned by the main query. For example, if
one wants to find the employees who earn more than the average salary of their
own department, then one has to enter:
SQL> SELECT DEPTNO, ENAME, SAL FROM EMP X WHERE
SAL>(SELECT AVG(SAL) FROM EMP WHERE X.DEPTNO=DEPTNO)
ORDER BY DEPTNO;
In this example, the subquery is executed for each row of the main query and it
computes the average salary for the employee's department. Finally, the main
query compares the employee's salary to the department's average salary. This
type of subquery where the alias name appears both in subquery and main query
is known as correlated subquery.
The next chapter explains the arithmetic and group functions in SQL*PLUS.

Arithmetic and Group Functions in SQL*Plus


Objectives
In this session, you will learn about Arithmetic Expressions, Group Functions, Date
Arithmetic and The NVL Function.

Topics

Arithmetic Expressions
Arithmetic Functions
Group Functions
Group Functions Vs Individual Functions
Date Arithmetic
The NVL Function

Arithmetic Expressions
You can perform a calculation based on numbers in the database by including
an arithmetic expression in a SQL command. An arithmetic expression consists
of a number column names and number values, connected by the arithmetic
operators.
You may use these operators in arithmetic expression:
+ Add, - Subtract, * Multiply and / Divide
Example: To calculate total compensation for all sales people, enter:
SQL> SELECT ENAME, SAL, COMM, SAL+COMM FROM EMP WHERE
JOB='SALESMAN';
Although SAL+COMM is not a column in the table, SQL*PLUS displays the
calculated results as if it were.
We can also include arithmetic logical expression in a where clause.
Example: To list employees whose commission is greater than 25% of their
salary, enter:
SQL> SELECT ENAME, SAL, COMM FROM EMP WHERE COMM >
0.25*SAL;
Here is another example, which calculates the annual compensation for all sales
people.
SQL> SELECT ENAME, SAL, COMM, 12*(SAL+COMM) FROM EMP
WHERE JOB='SALESMAN';
Note that if you omit the parenthesis, the multiplication will be performed
before the addition.

Arithmetic Functions
Arithmetic functions available in SQL*PLUS are listed below:
Function
ABS(expressison)
GREATEST(arg1,arg2)
LEAST(arg1,arg2)
ROUND(arg,decimal)
TO_NUMBER( char_arg)
TRUNC(arg,decimal)

Description
Absolute value of the expression
Returns arg1 or arg2 whichever is greater.
Returns arg1 or arg2 whichever is smaller.
Rounds the arg to specified decimal points.
Converts the character argument to a number.
Truncates the argument by specified decimal
points.

Example: To calculate the daily salary of employees in Department 30 enter:


SQL> SELECT ENAME, SAL, SAL/22, ROUND(SAL/22,2) FROM EMP
WHERE DEPTNO=30;
Note that in ROUND(SAL/22,2) function, the 2 after the comma means that
SQL*PLUS will round the result to two decimal places.
Similarly, we can truncate a number, which cuts off numbers to a specified
number of decimal places.

GROUP Functions
The functions presented in the previous section are individual; they return a
value for each row selected. But you can also use functions to get summary
information about groups of rows in your database. To get such information,
use a group function in your query. The table below lists the commonly used
group functions.
Function
AVG
COUNT
MAX
MIN
SUM

Example
AVG(SAL)
COUNT(COMM)
MAX(SAL)
MIN(SAL)
SUM(SAL)

Description
Average value of salary.
Total number of non-null Commissions.
Maximum of salary.
Minimum of salary.
Sum of salary

Example: To find the average salary of clerks, enter:


SQL> SELECT AVG(SAL) FROM EMP WHERE JOB = 'CLERK';
All the rows that satisfy the search condition are used to calculate the summary
information. Rather than displaying a value for each row selected, this query
calculates a single value AVG(SAL) as the result. You may also use group
functions with arithmetic expressions.
Example: To compute the average annual compensation of all sales people,
enter:
SQL> SELECT 12*AVG(SAL+COMM) FROM EMP WHERE
JOB='SALESMAN';
The COUNT function counts the number of non-null values, distinct number
values, or rows selected by the query.
Example: To count the employees, who are eligible to receive a commission,
enter:
SQL> SELECT COUNT(COMM) FROM EMP;
A special form of COUNT, COUNT(*) counts the number of rows that satisfy
the logical expression in the WHERE clause, if any.
Example: To count the number of employees in Department 30, enter:
SQL> SELECT COUNT(*) FROM EMP WHERE DEPTNO=30;

Group Functions Versus Individual Functions


If you include group functions in a select command, you may not select
individual results as well. For example, a command that begins SELECT
ENAME, AVG(SAL) is invalid. ENAME has a value for each row selected,
while AVG(SAL) has a single value for the whole query. If you enter such a
command, SQL*Plus will display a message saying that ENAME is "not a
single group set function".
If a select command contains a subquery, you may use group functions in the
subquery and select individual results in the main query, or vice versa in an
exception to the above rule. An example of a subquery used in this way is given
below.
A Group Function in a Subquery
Suppose you want to find out who makes the highest salary, Since you cannot
say SELECT ENAME, MAX(SAL), put the MAX(SAL) function in a subquery
instead:
Example: To list the employee and job with the highest salary, enter:
SQL> SELECT EMPNO, ENAME FROM EMP WHERE SAL=(SELECT
MAX(SAL) FROM EMP);
Group By Clause
Suppose you want to know the average salary of the employees in each
department. You could enter several separate AVG(SAL) queries, one per
department. But you can get the same information with a single query by using
the GROUP BY clause. The GROUP BY clause divides a table into groups of
rows so that the rows in each group have the same value in a specified column.
Example: To list the average salary in each department, enter:
SQL> SELECT DEPTNO, AVG(SAL) FROM EMP GROUP BY DEPTNO;
In this example, the GROUP by clause divides all the employees into groups
based on their department number. The group function AVG(SAL) is then
applied on the selected rows. If your SQL command contains a WHERE clause
also, place the GROUP BY clause after the WHERE clause.

Example: To count the employees, and calculate the average annual salary for
each job group in each department, enter:
SQL> SELECT DEPTNO, JOB, COUNT(*),12*AVG(SAL) FROM EMP
GROUP BY DEPTNO,JOB;
Just as one can select the specific row with a WHERE clause, one can also
select specific group by using the HAVING clause. Place the having clause
after the GROUP BY clause.
Example: To list the average annual salary for all job groups with more than
two employees, enter:
SQL> SELECT JOB, COUNT(*),12*AVG(SAL) FROM EMP GROUP BY JOB
HAVING COUNT(*)>2;
You may include both a WHERE clause and a HAVING clause in a query. In
that case, the WHERE clause selects the rows and the HAVING clause selects
the groups.
Example: To list all the departments with at least two clerks, enter:
SQL> SELECT DEPTNO FROM EMP WHERE JOB='CLERK' GROUP BY
DEPTNO HAVING COUNT(*) >=2;

Date Arithmetic
You can perform arithmetic operations on date fields. Dates can be added or
subtracted as if they were numeric.

Example:
SQL> SELECT SYSDATE+ 7 FROM DUAL;
Returns a date, which is one week from today's date. Similarly we can subtract a
number from date to find the date before the number of days.
Table below lists the commonly used date functions.

Function

Example

Result

ADD_MONTHS
GREATEST
LEAST
LAST_DAY

ADD_MONTHS(D,N)
GREATEST(D1,D2)
LEAST(D1,D2)
LAST_DAY(HIREDATE)

MONTHS_BETWEEN
NEXT_DAY

MONTHS_BETWEEN
NEXT_DAY(DATE,'DAY')

ROUND

ROUND(DATE)

Date D plus N months


Later of D1 or D2
Earlier of D1 or D2
Last day of month Containing the
HIREDATE
Months between two dates.
Date of first Day after the
specified date.
Rounds the date to the Nearest day.

TO_CHAR

TO_CHAR(DATE,'FORM
AT')
TO_DATE(CHARDATE,
'INTERPRETATION')

Converts the date to the specified


character format.
Converts the character date to a
standard date.

TO_DATE

The table below shows the available character formats, which can be used in the
TO_CHAR function.
Format
(none)
MM/DD/YY
DD.MM.YYYY
DY DD MON YY
Day Mon DD
Day Month DD YYYY
DDTH "OF" MONTH

Example
12-jan-90 (Default)
01/12/90
12.01.1990
FRI 12 JAN 90
Friday Jan 12
Friday January 12 1990
12th OF JANUARY

Example: To display employee's hire dates in a format like "Friday the 12th of
January 1990", enter:
SQL> SELECT ENAME, JOB, TO_CHAR(HIREDATE,'DAY "the" ddth "of"
Month YYYY') "HIRE
DATE" FROM EMP;
Here, note that the label "HIRE DATE" replaces the second column in the query
result.
The between-and operator can also be used for searching a range of date values.
Example: To list the employees, who were hired between January 4th 1981,
and April 15th 1981,enter:
SQL> SELECT EMPNO, ENAME FROM EMP WHERE HIREDATE
BETWEEN '4-JAN-81' AND '15-APR-81' ORDER BY HIREDATE;

Here is an example, which uses a GROUP BY clause with dates.


Example: To count the employees hired in each year, enter:
SQL> SELECT TO_CHAR(HIREDATE,'YYYY') "HIREDATE",COUNT(*)
FROM EMP GROUP BY TO_CHAR(HIREDATE,'YYYY');

The NVL Function


Often you will want to treat the NULL values as zero (or some other value) in a
query. For example in calculating the total salary, a null commission has to be
treated as zero. For that we can use the NVL (null value) function, which
assigns a specified value to a column, if the column is null.
For example, if one wants to calculate the total compensation of all employees,
one has to enter:
SQL> SELECT ENAME, JOB, SAL, COMM, SAL+NVL(COMM,0) FROM
EMP;
The above tells SQL*PLUS to treat a null commission as zero. Note that by
using this function, we can convert a null value to any specified value, not just
to zero.
So far we have been discussing only one database object, which is table. In the
next chapter, we will learn about more database objects.

Oracle Lab - Queries


Objectives
In this session, you will use the Author, Book and Studies Table and retrieve records
from them.

Topics

Section I - Problems
Section I Solutions
Section II - Problems
Section II Solutions
Section III - Problems
Section III - Solutions
Section IV - Problems
Section IV - Solutions

SECTION 1
PROBLEMS
1.1. Find out the SELLING COST AVERAGE for books written in HINDI.
1.2. Display the NAMES AND AGES of all the authors.
1.3. Display the NAMES of those who have done the B.Com course.
1.4. Which book sold the HIGHEST number of copies?
1.5. Display the NAMES and DATE OF BIRTH of all the authors born in
JULY.
1.6. Display the LOWEST SELLING COST OF THE BOOK.
1.7. How many authors have done the course in OXFORD University?
1.8. How much STEPHEN has been earned through sale of books written in
HINDI?
1.9. Display the list of BOOKS written by STEPHEN.
1.10. How many authors have done the B.A. course?
1.11. Display the details of BOOKS whose sales CROSSED the number 45.
1.12. Find out the NUMBER OF COPIES of books sold written by 'LUCILLE'.
1.13. What is the price of the costliest book written in TAMIL?
1.14. How many books were written in TAMIL?
1.15. How many authors studied at HARWARD?
1.16. How many authors paid an amount between 9000 and 20000 for their
course?
1.17. What is the average course fee?
1.18. Display the details of authors knowing JAPANESE.
1.19.How many authors know either TAMIL or HINDI?
1.20. How many authors don't know TAMIL?
1.21. How old is the oldest male author?

1.22. What is the average age of female authors?


1.23. Calculate the experience in years for each author and display the same
along with the names in descending order of experience.
1.24. Who are the authors who celebrate their birthdays during the current
month (For example, the Month of May).
1.25. How many female authors are there?
1.26. Which are the languages known by the male authors?
1.27. What is the AVERAGE salary of authors?
1.28. How many people draw a salary between 2000 and 3000?
1.29. Display the details of those who don't know ENGLISH, LATIN or
TAMIL.
1.30. How many female authors knowing JAPANESE are above 24 years of
age?
1.31. Display the details of AUTHORS with LESS than a year's EXPERIENCE.
1.32. Display the details of those who will be COMPLETING 2 years of service
this YEAR.
1.33. Find out the TOTAL selling cost of the books written by DIANA.
1.34. Display the University names from the studies table without duplicates.
1.35. How many different courses are mentioned in the studies table?
1.36. Display the names of the authors whose names contain 2 occurrence of the
letter 'A'.
1.37. Display the names of authors whose name contains 5 characters.
1.38. How many male authors knowing LATIN have more than 2 years
experience?
1.39. What is the length of the shortest name in the author table?
1.40. What is the average writing cost of books written in LATIN?
1.41. Display the name, sex, DOB (DD/MM/YY format), DOJ (DD/MMM/YY
format) for all the authors.
1.42. What is the total salary paid in a month to male authors who don't know
LATIN?

1.43. Who are the authors who were born on the LAST DAY of the MONTH?
1.44. Display the title, bcost, wcost and DIFFERENCE between BCOST and
WCOST in DESCENDING order of DIFFERENCE.
1.45. Display the names of the books whose names contain more than 2 words.
1.46. Display the name, DOB, DOJ of those authors whose month of birth and
month of joining are the same.
NOTE: Solutions are given at the end. However it is better that you
attempt the solution on your own and refer to the Solutions only in case of
doubt or to confirm the solution.

SECTION 1: SOLUTIONS
SOLUTION 1.1
SQL> SELECT AVG(BCOST) FROM BOOK WHERE WRI_IN='HINDI' ;
AVG(BCOST)
---------275
1 row selected.
SOLUTION 1.2
SQL> SELECT NAME, ROUND(MONTHS_BETWEEN(SYSDATE, DOB) / 12)
"AGE" FROM AUTHOR ;
NAME
-------------------RANDY
DANIEL
SOLOMON
ROSY
CATHARINE
DIANA
BRAIN
LUKE
STEWART
STEPHEN
ELIZABETH
ANITA
LUCILLE
MAUREEN
14 rows selected.

AGE
--------32
28
28
23
25
24
28
32
33
26
23
24
28
22

SOLUTION 1.3
SQL> SELECT NAME FROM STUDIES WHERE COURSE = 'B.COM';
NAME
-------------------DANIEL
SOLOMON
ROSY
MAUREEN
4 rows selected.
SOLUTION 1.4
SQL> SELECT TITLE FROM BOOK WHERE SOLD=(SELECT MAX(SOLD)
FROM BOOK);
TITLE
------------------------SELF COOKING
1 rows selected.
SOLUTION 1.5
SQL> SELECT NAME, DOB FROM AUTHOR WHERE
TO_CHAR(DOB,'MON')='JUL';
NAME
-------------------STEPHEN

DOB
--------20-JUL-72

1 rows selected.
SOLUTION 1.6
SQL> SELECT MIN(BCOST) "LOWEST COST" FROM BOOK;
LOWEST COST
----------------------90
1 rows selected.

SOLUTION 1.7
SQL> SELECT COUNT(NAME) "NO OF AUTHORS" FROM STUDIES
WHERE UNIVER='OXFORD' ;
NO OF AUTHORS
----------------------------4
1 row selected.
SOLUTION 1.8
SQL> SELECT SUM(BCOST * SOLD ) "RESTEPHENE" FROM BOOK
WHERE WRI_IN= 'HINDI' ;
RESTEPHENE
--------18250
1 row selected.
SOLUTION 1.9
SQL> SELECT TITLE FROM BOOK WHERE NAME='STEPHEN';
TITLE
-----------------PROGRAMMING IN C++
GRE ENTRANCE EXAMS
2 rows selected.
SOLUTION 1.10
SQL> SELECT COUNT(NAME) "NO OF AUTHORS" FROM STUDIES
WHERE COURSE ='B.A' ;
NO OF AUTHORS
------------1
1 rows selected.

SOLUTION 1.11
SQL >SELECT TITLE, NAME "AUTHOR", WRI_IN FROM BOOK WHERE
SOLD > 45;
TITLE
------------------------GENERAL KNOWLEDGE
INTERIOR DECORATION
SELF COOKING

AUTHOR
-------------------RANDY
ANITA
ANITA

WRI_IN
-------------------URUDU
JAPANESE
ARABIC

3 rows selected.
SOLUTION 1.12
SQL > SELECT SUM(SOLD) "NO OF COPIES" FROM BOOK WHERE
NAME= 'LUCILLE' ;
NO OF COPIES
-----------50
1 rows selected.
SOLUTION 1.13
SQL> SELECT MAX(BCOST) "MAXIMUM PRICE" FROM BOOK WHERE
WRI_IN='TAMIL';
MAXIMUM PRICE
------------550
1 rows selected.
SOLUTION 1.14
SQL> SELECT COUNT(TITLE) "NO OF BOOKS" FROM BOOK WHERE
WRI_IN='TAMIL' ;
NO OF BOOKS
----------4
1 rows selected.

SOLUTION 1.15
SQL> SELECT COUNT(NAME) "NO OF AUTHORS" FROM STUDIES
WHERE UNIVER= 'HARWARD' ;
NO OF AUTHORS
------------3
3 rows selected
SOLUTION 1.16
SQL> SELECT COUNT(NAME) "NO OF AUTHORS" FROM STUDIES
WHERE CCOST BETWEEN 9000 AND 20000 ;
NO OF AUTHORS
------------6
1 row selected.
SOLUTION 1.17
SQL> SELECT AVG(CCOST) "AVERAGE COURSE FEE" FROM STUDIES;
AVERAGE COURSE FEE
-----------------31928.571
1 row selected.

SOLUTION 1.18
SQL> SELECT NAME, SALARY, SEX FROM AUTHOR WHERE
LANG1='JAPANESE' OR LANG2='JAPANESE';
NAME
-------------------CATHARINE
STEWART
ANITA
MAUREEN

SALARY
--------3000
3100
3100
5000

S
F
M
F
F

4 rows selected.
SOLUTION 1.19

SQL> SELECT COUNT(NAME) "NO OF AUTHORS" FROM AUTHOR


WHERE LANG1 IN ('TAMIL','HINDI') OR LANG2 IN ('TAMIL','HINDI');
NO OF AUTHORS
------------6
1 row selected.
SOLUTION 1.20
SQL> SELECT COUNT(NAME) "NO OF AUTHORS" FROM AUTHOR
WHERE LANG1 <> 'TAMIL' AND LANG2 <> 'TAMIL';
NO OF AUTHORS
------------10
1 row selected.

SOLUTION 1.21
SQL> SELECT ROUND(MONTHS_BETWEEN(SYSDATE,DOB)/12,2) "AGE"
FROM AUTHOR WHERE DOB=(SELECT MIN(DOB) FROM AUTHOR
WHERE SEX='M');
AGE
--------32.75
1 row selected.
SOLUTION 1.22
SQL> SELECT AVG(ROUND(MONTHS_BETWEEN(SYSDATE,DOB)/12,2))
"AVERAGE AGE" FROM AUTHOR WHERE SEX='F';
AVERAGE AGE
----------------------24.328571
1 row selected.
SOLUTION 1.23
SQL> SELECT NAME, ROUND(MONTHS_BETWEEN(SYSDATE,DOJ)/12,2)
"YEARS OF EXPERIENCE" FROM AUTHOR ORDER BY 2 DESC;
NAME
-------------------LUKE
DANIEL
STEWART
BRAIN
LUCILLE
RANDY
STEPHEN
SOLOMON
CATHARINE
DIANA
MAUREEN
ROSY
ANITA
ELIZABETH
14 rows selected.

YEARS OF EXPERIENCE
------------------8.13
6.18
5.11
4.9
4.32
4.12
3.69
3.63
3.39
1.81
1.56
.7
.6
.14

SOLUTION 1.24
SQL> SELECT NAME,DOB FROM AUTHOR WHERE
TO_CHAR(DOB,'MON')=TO_CHAR(SYSDATE,'MON');
NAME
-------------------DANIEL

DOB
--------19-MAY-70

1 row selected.
SOLUTION 1.25
SQL> SELECT COUNT(NAME) "NO OF FEMALES" FROM AUTHOR
WHERE SEX= 'F' ;
NO OF FEMALES
-------------------------7
1 row selected.
SOLUTION 1.26
SQL> SELECT LANG1 FROM AUTHOR WHERE SEX='M'
UNION SELECT LANG2 FROM AUTHOR WHERE SEX='M';
LANG1
-------------------ENGLISH
HINDI
LATIN
JAPANESE
GERMAN
ARABIC
TAMIL
LATIN
URUDU
9 rows selected.

SOLUTION 1.27
SQL> SELECT ROUND(AVG(SALARY)) "AVERAGE SALARY" FROM
AUTHOR ;
AVERAGE SALARY
----------------------------3471
1 row selected.
SOLUTION 1.28
SQL> SELECT COUNT(NAME) "NO OF AUTHORS" FROM AUTHOR
WHERE SALARY BETWEEN 2000 AND 3000;
NO OF AUTHORS
------------5
1 row selected.
SOLUTION 1.29
SQL> SELECT NAME, LANG1, LANG2, SALARY FROM AUTHOR WHERE
LANG1 NOT IN('ENGLISH','LATIN','TAMIL') AND LANG2 NOT
IN('ENGLISH','LATIN','TAMIL');
NAME
-----------SOLOMON
CATHARINE
DIANA
STEWART
ANITA
MAUREEN

6 rows selected.

LANG1
-----------------HINDI
JAPANESE
GREEK
ARABIC
JAPANESE
FRENCH

LANG2
-----------------GERMAN
LATIN
HINDI
JAPANESE
ARABIC
JAPANESE

SALARY
--------4400
3000
5000
3100
3100
5000

SOLUTION 1.30
SQL> SELECT COUNT(NAME) "NO OF AUTHORS" FROM AUTHOR
WHERE
SEX='F' AND (LANG1='JAPANESE' OR LANG2='JAPANESE') AND
MONTHS_BETWEEN(SYSDATE,DOB)/12 > 24;
NO OF AUTHORS
------------2
1 row selected.
SOLUTION 1.31
SQL>SELECT NAME, ROUND(MONTHS_BETWEEN(SYSDATE,DOJ)/12,2)
"EXPERIENCE", SALARY FROM AUTHOR WHERE
MONTHS_BETWEEN(SYSDATE,DOJ) < 12;
NAME
-------------------ROSY
ELIZABETH
ANITA

EXPERIENCE
---------.7
.14
.6

SALARY
--------3100
2500
3100

3 rows selected.
SOLUTION 1.32
SQL> SELECT NAME, ROUND(MONTHS_BETWEEN(SYSDATE,DOJ)/12,2)
"EXPERIENCE", SALARY FROM AUTHOR WHERE TO_CHAR(DOJ,'YYYY')
+ 2=TO_CHAR(SYSDATE,'YYYY');
NAME
-------------------DIANA
MAUREEN
2 rows selected.

EXPERIENCE
---------1.81
1.56

SALARY
--------5000
5000

SOLUTION 1.33
SQL> SELECT SUM(BCOST) "TOTAL COST" FROM BOOK WHERE
NAME='DIANA' ;
TOTAL COST
-------------------1200
1 row selected.
SOLUTION 1.34
SQL> SELECT DISTINCT UNIVER FROM STUDIES;
UNIVER
-------------------HARWARD
SYDNEY
ALASKA
OXFORD
CALIFORNIA
CAMBRIDGE
FLORIDA
BOMBAY
8 rows selected.
SOLUTION 1.35
SQL> SELECT COUNT(DISTINCT COURSE) "NO OF COURSES" FROM
STUDIES;
NO OF COURSES
------------8
1 row selected.

SOLUTION 1.36

SQL>SELECT NAME FROM AUTHOR WHERE INSTR(NAME,'A',1,2) <> 0


AND INSTR(NAME,'A',1,3) = 0;
NAME
-------------------CATHARINE
ANITA
DIANA
3 rows selected.
SOLUTION 1.37
SQL> SELECT NAME FROM AUTHOR WHERE LENGTH(NAME)=5;
NAME
-------------------DIANA
ANITA
BRAIN
RANDY
4 rows selected.
SOLUTION 1.38
SQL> SELECT COUNT(NAME) "NO OF AUTHROS" FROM AUTHOR
WHERE SEX='M' AND (LANG1='LATIN' OR LANG2='LATIN') AND
MONTHS_BETWEEN(SYSDATE,DOJ) > 24;

NO OF AUTHROS
------------2
1 row selected.

SOLUTION 1.39
SQL> SELECT MIN(LENGTH(NAME)) "SHORTEST LENGTH" FROM
AUTHOR;
SHORTEST LENGTH
--------------4
1 row selected.
SOLUTION 1.40
SQL> SELECT AVG(WCOST) "AVERAGE WRITTEN COST" FROM BOOK
WHERE WRI_IN='LATIN';
AVERAGE WRITTEN COST
----------------------------------------125
1 row selected.
SOLUTION 1.41
SQL>SELECT NAME, SEX, TO_CHAR(DOB,'DD/MM/YY') "DOB",
TO_CHAR(DOJ,'DD/MM/YY') "DOJ" FROM AUTHOR;
NAME
-------------------RANDY
DANIEL
SOLOMON
ROSY
CATHARINE
DIANA
BRAIN
LUKE
STEWART
STEPHEN
ELIZABETH
ANITA
LUCILLE
MAUREEN
14 rows selected.

S
-M
M
M
F
F
F
M
M
M
M
F
F
F
F

DOB
---------12/04/66
19/05/70
10/10/70
25/01/75
22/10/73
30/06/74
26/09/70
30/11/65
28/08/65
20/07/72
03/01/75
30/04/74
02/12/69
03/12/75

DOJ
---------12/04/94
21/03/92
10/10/94
16/09/97
05/01/95
06/08/96
04/07/93
11/04/90
19/04/93
18/09/94
05/04/98
23/10/97
02/02/94
04/11/96

SOLUTION 1.42
SQL> SELECT SUM(SALARY) "TOTAL SALARY" FROM AUTHOR WHERE
SEX='M' AND (LANG1 <>'LATIN' AND LANG2 <> 'LATIN');
TOTAL SALARY
-----------18000
1 row selected.
SOLUTION 1.43
SQL> SELECT NAME, DOB FROM AUTHOR WHERE DOB =
LAST_DAY(DOB);
NAME
-------------------DIANA
LUKE
ANITA

DOB
--------30-JUN-74
30-NOV-65
30-APR-74

3 rows selected.
SOLUTION 1.44
SQL> SELECT TITLE, BCOST, WCOST, ABS(BCOSTWCOST)"DIFFERENCE" FROM BOOK ORDER BY 4 DESC;
TITLE
------------------------INTERIOR DECORATION
LEARN ARCHITECTURE
WONDERFUL TALES
GRE ENTRANCE EXAMS
PROGRAMMING IN C++
GENERAL KNOWLEDGE
CURRENT COMPUTERS
ACCOUNTING POLICY
KNOW YOUR ENGLISH
ACCOUNTING POLICY
EXCISE POLICY
STATISTICS
JAPANESE IN 30 DAYS
KNOW YOUR SALES TAX
BANKING
BEAUTY TIPS
PERSONALITY EVALUATOR
SELF COOKING
DO IT YOURSELF

19 rows selected.

BCOST
--------750
500
650
550
500
450
500
450
300
350
600
350
250
200
250
200
150
90
125

WCOST
--------400
225
400
300
250
250
300
250
100
200
450
200
125
100
150
120
80
40
80

DIFFERENCE
---------350
275
250
250
250
200
200
200
200
150
150
150
125
100
100
80
70
50
45

SOLUTION 1.45
SQL> SELECT TITLE FROM BOOK WHERE INSTR(TITLE,' ',1,2) > 0 ;
TITLE
------------------------KNOW YOUR ENGLISH
JAPANESE IN 30 DAYS
KNOW YOUR SALES TAX
LEARN ARCHITECTURE
PROGRAMMING IN C++
GRE ENTRANCE EXAMS
DO IT YOURSELF
7 rows selected.
SOLUTION 1.46
SQL> SELECT NAME, DOB, DOJ FROM AUTHOR WHERE
TO_CHAR(DOB,'MON')=TO_CHAR(DOJ,'MON');
NAME
-------------------RANDY
SOLOMON
ANITA
3 rows selected.

DOB
--------12-APR-66
10-OCT-70
30-APR-74

DOJ
--------18-APR-94
10-OCT-94
23-APR-97

SECTION 2
2.1. Display the number of books written in each language.
2.2. Display the number of books written by each author.
2.3. Display the number of male and female authors.
2.4. Display the costliest book written in each language. Note: The costliest book is the
one, which has maximum sale price.
2.5. Display the number of authors BORN in each year.
2.6. Display the number of authors who have JOINED each year.
2.7. Display the number of authors BORN in each month.
2.8. Display the number of authors JOINED each month.
2.9. Display the language-wise COUNT OF lang 1.
2.10. Display the language-wise COUNT of lang 2.
2.11. Display the number of authors in each salary group.
2.12. Display the number of authors who studied in each University.
2.13. Display the number of authors who studied in each course.
2.14. Display the TOTAL written cost of the books written in each language.
2.15. Display the TOTAL selling cost of the books written in each language.
2.16. Display the average written cost of the book written by each author.
2.17. Display the total writing cost of the books written by the each author.
2.18. Display the number of books sold for each author.
2.19. Display the minimum sales price of the book written by each author.
2.20. Display each language name with its average written cost and its average selling
cost.
2.21. Display each university name with number of courses, average cost per course.
2.22. Display each University name with number of students.
2.23. Display the names of AUTHORS who have written more than one book.

2.24. Display the authors who have not written any books.
2.25. Display the number of books written in each language except JAPANESE &
GREEK.
2.26. Display the number of books in each language for which written cost is less than
200.
2.27. Display the average difference between bcost and wcost for each language.
2.28. Display highest, lowest and average salaries for the SALARY GROUP greater
than 3000.
NOTE: Solutions are given at the end. However it is better that you attempt the
solution on your own and refer to the Solutions only in case of doubt or to confirm
the solution.

SOLUTIONS: SECTION 2
SOLUTION 2.1
SQL> SELECT WRI_IN, COUNT(*) "NO OF BOOKS" FROM BOOK GROUP
BY WRI_IN;
WRI_IN
------------------------HINDI
LATIN
JAPANESE
GERMAN
GREEK
ARABIC
TAMIL
LATIN
URUDU

NO OF BOOKS
----------2
2
3
1
2
2
4
1
2

9 rows selected.
SOLUTION 2.2
SQL> SELECT NAME, COUNT(*) "NO OF BOOKS" FROM BOOK GROUP
BY NAME;
NAME
-------------------DIANA
LUCILLE
CATHARINE
MAUREEN
ANITA
RANDY
ROSY
STEWART
SOLOMON
LUKE
STEPHEN
11 rows selected.

NO OF BOOKS
----------3
2
1
1
2
2
1
2
2
1
2

SOLUTION 2.3
SQL> SELECT SEX, COUNT(*)"NO OF AUTHORS" FROM AUTHOR
GROUP BY SEX ;
S
F
M

NO OF AUTHORS
--------7
7

2 rows selected.
SOLUTION 2.4
SQL> SELECT WRI_IN, TITLE FROM BOOK X WHERE BCOST=
(SELECT MAX(BCOST) FROM BOOK WHERE X.WRI_IN=WRI_IN);
WRI_IN
TITLE
------------------------- ------------------------URUDU
GENERAL KNOWLEDGE
GERMAN
SHORT STORIES
HINDI
KNOW YOUR ENGLISH
LATIN
JAPANESE IN 30 DAYS
GREEK
LEARN ARCHITECTURE
ARABIC
EXCISE POLICY
LATIN
PROGRAMMING IN C++
TAMIL
GRE ENTRANCE EXAMS
JAPANESE
INTERIOR DECORATION
9 rows selected.
SOLUTION 2.5
SQL>SELECT TO_CHAR(DOB,'YYYY'),"YEAR",COUNT(NAME)"NO OF
AUTHORS" FROM AUTHOR GROUP BY TO_CHAR(DOB,'YYYY');
YEAR
----1965
1966
1969
1970
1972
1973
1974
1975

NO OF AUTHORS
-----------2
1
1
3
1
1
2
3

8 rows selected.

SOLUTION 2.6
SQL>SELECT TO_CHAR(DOB,'YYYY'),"YEAR",COUNT(NAME)"NO OF
AUTHORS" FROM AUTHOR GROUP BY TO_CHAR(DOB,'YYYY');
YEAR
----1990
1992
1993
1994
1995
1996
1997
1998

NO OF AUTHORS
-----------1
1
2
4
1
2
2
1

SOLUTION 2.7
SQL> SELECT TO_CHAR(DOB,'MONTH') "MONTH",COUNT(NAME) "NO
OF AUTHORS" FROM AUTHOR GROUP BY TO_CHAR(DOB,'MONTH')
ORDER BY TO_DATE(TO_CHAR(DOB,'MONTH'),'MONTH');
MONTH
---------JANUARY
APRIL
MAY
JUNE
JULY
AUGUST
SEPTEMBER
OCTOBER
NOVEMBER
DECEMBER
10 rows selected.

NO OF AUTHORS
-----------2
2
1
1
1
1
1
2
1
2

SOLUTION 2.8
SQL> SELECT TO_CHAR(DOJ,'MONTH') "MONTH",COUNT(NAME) "NO
OF AUTHORS" FROM AUTHOR GROUP BY TO_CHAR(DOJ,'MONTH')
ORDER BY TO_DATE(TO_CHAR(DOJ,'MONTH'),'MONTH');
MONTH
NO OF AUTHORS
--------------------JANUARY 1
FEBRUARY 2
MARCH
1
APRIL
5
JULY
1
AUGUST
1
SEPTEMBER 1
OCTOBER 1
NOVEMBER 1
9 rows selected.
SOLUTION 2.9
SQL> SELECT LANG1 "LANGUAGE", COUNT(LANG1) "NO.OF
OCCURENCE" FROM AUTHOR GROUP BY LANG1;
LANGUAGE
------------------------ENGLISH
FRENCH
HINDI
JAPANESE
GREEK
ARABIC
TAMIL
LATIN
URUDU
9 rows selected.

NO.OF OCCURENCE
--------------1
1
1
2
1
1
4
2
1

SOLUTION 2.10
SQL> SELECT LANG2 "LANGUAGE", COUNT(LANG2) "NO.OF
OCCURENCE" FROM AUTHOR GROUP BY LANG2;
LANGUAGE
------------------------ENGLISH
HINDI
LATIN
JAPANESE
GERMAN
ARABIC
LATIN
URUDU

NO.OF OCCURENCE
--------------1
1
4
2
1
1
2
2

8 rows selected.
SOLUTION 2.11
SQL> SELECT SALARY, COUNT(NAME)"NO OF AUTHORS" FROM
AUTHOR GROUP BY SALARY;
SALARY
--------2500
2900
3000
3100
3500
3800
4400
5000

NO OF AUTHORS
-----------2
2
1
3
1
2
1
2

8 rows selected.

SOLUTION 2.12
SQL> SELECT UNIVER, COUNT(NAME)"NO OF AUTHORS" FROM
STUDIES GROUP BY UNIVER;
UNIVER
------------------------HARWARD
SYDNEY
ALASKA
OXFORD
CALIFORNIA
CAMBRIDGE
FLORIDA
BOMBAY

NO OF AUTHORS
-----------3
2
1
4
1
1
1
1

8 rows selected.
SOLUTION 2.13
SQL> SELECT COURSE, COUNT(NAME)"NO OF AUTHORS" FROM
STUDIES GROUP BY COURSE;
COURSE
---------B.A
B.COM
B.E
B.SC
M.A
M.COM
M.E
M.SC

NO OF AUTHORS
-----------1
4
1
1
1
1
2
3

8 rows selected.

SOLUTION 2.14
SQL> SELECT WRI_IN "LANGUAGE", SUM(WCOST) "TOTAL COST"
FROM BOOK GROUP BY WRI_IN;
LANGUAGE
------------------------HINDI
LATIN
JAPANESE
GERMAN
GREEK
ARABIC
TAMIL
LATIN
URUDU

TOTAL COST
---------250
350
820
400
475
490
780
125
330

9 rows selected.
SOLUTION 2.15
SQL> SELECT WRI_IN "LANGUAGE", SUM(BCOST) "TOTAL COST" FROM
BOOK GROUP BY WRI_IN;
LANGUAGE
------------------------HINDI
LATIN
JAPANESE
GERMAN
GREEK
ARABIC
TAMIL
LATIN
URUDU
9 rows selected.

TOTAL COST
---------550
700
1450
650
950
690
375
250
600

SOLUTION 2.16
SQL> SELECT NAME, AVG(WCOST)"AVERAGE COST" FROM BOOK
GROUP BY NAME;
NAME
-------------------DIANA
LUCILLE
CATHARINE
MAUREEN
ANITA
RANDY
ROSY
STEWART
SOLOMON
LUKE
STEPHEN

AVERAGE COST
-----------208.33333
80
100
120
220
225
125
375
250
200
275

11 rows selected.
SOLUTION 2.17
SQL> SELECT NAME, SUM(WCOST) "TOTAL COST" FROM BOOK GROUP
BY NAME;
NAME
-------------------DIANA
LUCILLE
CATHARINE
MAUREEN
ANITA
RANDY
ROSY
STEWART
SOLOMON
LUKE
STEPHEN
11 rows selected.

TOTAL COST
---------625
160
100
120
440
450
125
750
500
200
550

SOLUTION 2.18
SQL> SELECT NAME, SUM(SOLD)"NO OF BOOKS" FROM BOOK GROUP
BY NAME;
NAME
-------------------DIANA
LUCILLE
CATHARINE
MAUREEN
ANITA
RANDY
ROSY
STEWART
SOLOMON
LUKE
STEPHEN

NO OF BOOKS
----------90
50
15
40
130
100
25
75
75
30
80

11 rows selected.
SOLUTION 2.19
SQL> SELECT NAME, MIN(BCOST) "MINIMUM COST" FROM BOOK
GROUP BY NAME;
NAME
-------------------DIANA
LUCILLE
CATHARINE
MAUREEN
ANITA
RANDY
ROSY
STEWART
SOLOMON
LUKE
STEPHEN
11 rows selected.

MINIMUM COST
-----------250
125
200
200
90
350
250
500
300
350
500

SOLUTION 2.20
SQL> SELECT WRI_IN "LANGUAGE", AVG(WCOST) "AVERAGE WRITTEN
COST" , AVG(BCOST) "AVERAGE SELLING COST" FROM BOOK GROUP
BY WRI_IN;
LANGUAGE AVERAGE WRITTEN COST
-------------------- -------------------HINDI
125
LATIN
175
JAPANESE
273.33333
GERMAN
400
GREEK
237.5
ARABIC
245
TAMIL
195
LATIN
125
URUDU
165

AVERAGE SELLING COST


-------------------275
350
483.33333
650
475
345
343.75
250
300

9 rows selected.
SOLUTION 2.21
SQL> SELECT UNIVER,COUNT(COURSE) "NO OF COURSES",
AVG(CCOST) "AVERAGE COST" FROM STUDIES GROUP BY UNIVER;

UNIVER
-------------------HARWARD
SYDNEY
ALASKA
OXFORD
CALIFORNIA
CAMBRIDGE
FLORIDA
BOMBAY

NO OF COURSES
------------3
2
1
4
1
1
1
1

8 rows selected.

AVERAGE COST
-----------40000
32000
30000
45000
11000
15000
12000
15000

SOLUTION 2.22
SQL> SELECT UNIVER, COUNT(NAME) "NO OF STUDENT" FROM
STUDIES GROUP BY UNIVER;
UNIVER
-------------------HARWARD
SYDNEY
ALASKA
OXFORD
CALIFORNIA
CAMBRIDGE
FLORIDA
BOMBAY

NO OF STUDENT
------------3
2
1
4
1
1
1
1

8 rows selected.
SOLUTION 2.23
SQL> SELECT NAME, COUNT(TITLE) "NO OF BOOKS" FROM BOOK
GROUP BY NAME HAVING COUNT(TITLE) > 1;
NAME
-------------------DIANA
LUCILLE
ANITA
RANDY
STEWART
SOLOMON
STEPHEN
7 rows selected.

NO OF BOOKS
----------3
2
2
2
2
2
2

SOLUTION 2.24
SQL> SELECT NAME FROM AUTHOR WHERE NAME NOT IN
(SELECT NAME FROM BOOK);
NAME
-------------------DANIEL
BRAIN
ELIZABETH
3 rows selected.
SOLUTION 2.25
SQL> SELECT WRI_IN, COUNT(TITLE) "NO OF BOOKS" FROM BOOK
WHERE WRI_IN NOT IN ('JAPANESE','GREEK') GROUP BY WRI_IN;
WRI_IN
-------------------HINDI
LATIN
GERMAN
ARABIC
TAMIL
LATIN
URUDU
7 rows selected.

NO OF BOOKS
----------2
2
1
2
4
1
2

SOLUTION 2.26
SQL> SELECT WRI_IN "LANGUAGE", COUNT(TITLE) "NO OF BOOKS"
FROM BOOK WHERE WCOST < 200 GROUP BY WRI_IN;
LANGUAGE
-------------------HINDI
LATIN
JAPANESE
ARABIC
TAMIL
LATIN
URUDU
7 rows selected.

NO OF BOOKS
----------2
1
1
1
1
1
1

SOLUTION 2.27
SQL> SELECT WRI_IN "LANGUAGE", AVG(BCOST-WCOST) "AVERAGE
DIFFERENCE" FROM BOOK GROUP BY WRI_IN;
LANGUAGE
-------------------HINDI
LATIN
JAPANESE
GERMAN
GREEK
ARABIC
TAMIL
LATIN
URUDU
9 rows selected.

AVERAGE DIFFERENCE
-----------------150
175
210
250
237.5
100
148.75
125
135

SOLUTION 2.28
SQL> SELECT MAX(SALARY) "MAXIMUM SALARY",MIN(SALARY)
"MINIMUM SALARY", AVG(SALARY) "MID SALARY" FROM AUTHOR
WHERE SALARY > 3000;
MAXIMUM SALARY
-------------5000
1 row selected.

MINIMUM SALARY
-------------3100

MID SALARY
---------3866.6667

LAB: SECTION 3
3.1. Who is the highest paid JAPANESE author?
3.2. Who is the highest paid female LATIN author?
3.3. Display the names of the highest paid author for each language (lang1)?
3.4. Who is the least experienced author?
3.5. Who is the most experienced male author knowing TAMIL?
3.6. Who is the youngest author knowing LATIN?
3.7. Which female author is earning more than 3000 and doesn't know either
JAPANESE, GREEK, HINDI or LATIN?
3.8. Which University has the most number of students?
3.9. Which course has been done by the most of the authors?
3.10. Display the name of the university and course, which has a course fee that is
below the AVERAGE course fee.
3.11. Which is the costliest course?
3.12. Which university conducts the costliest course?
3.13. Which courses have students, below the average number of students?
3.14. Which Universities conduct the courses that have the course fee more than
15000?
3.15. Display the names of the courses whose fees are within 5000/- (+ or -) of the
average fee.
3.16. Which book has the highest written cost?
3.17. Which book has the lowest selling cost?
3.18. Who has written the book that has sold least number of copies?
3.19. Which language was used to write the book, which has the highest sales amount?
Note sales amount = no of copies sold X book sales cost.
3.20. How many copies of the book were sold which has the least difference
between written and selling cost?
3.21. Which is the costliest book written in TAMIL?

3.22. Which language was used to write the most number of books?
3.23. Which author has written the highest number of books?
3.24. Who is the author of the book, which has the maximum sales cost?
3.25. Display the names of the books, which sold less than the average number of
copies sold.
3.26. Display the author names and the cheapest book written by them in each
language.
3.27. Who is the youngest male author born in 1970?
3.28. Who is the oldest female author who joined in 1996?
3.29. In which year were the most number of authors born?
3.30. In which month did most number of the authors join?
3.31. Who are the male authors earning below the average salary of female authors?
3.32. Who are the female authors earning more than the highest paid male author?
3.33. Which language has been stated as lang 1 by the most of the authors?
NOTE: Solutions are given at the end. However it is better that you attempt the
solution on your own and refer to the Solutions only in case of doubt or to confirm
the solution.

SOLUTIONS: SECTION 3
SOLUTION 3.1
SQL> SELECT NAME, SALARY FROM AUTHOR WHERE
(LANG1='JAPANESE' OR LANG2='JAPANESE') AND SALARY = (SELECT
MAX(SALARY) FROM AUTHOR WHERE LANG1='JAPANESE' OR
LANG2='JAPANESE');
NAME
-------------------MAUREEN

SALARY
--------5000

1 row selected.
SOLUTION 3.2
SQL> SELECT NAME,SALARY FROM AUTHOR WHERE (LANG1='LATIN'
OR LANG2='LATIN') AND SEX='F' AND SALARY =(SELECT MAX(SALARY)
FROM AUTHOR WHERE LANG1='LATIN' OR LANG2='LATIN' AND
SEX='F')
NAME
-------------------ROSY
1 row selected.

SALARY
--------3100

SOLUTION 3.3
SQL> SELECT NAME,SALARY,LANG1 FROM AUTHOR X WHERE
SALARY =(SELECT MAX(SALARY) FROM AUTHOR
WHERE X.LANG1=LANG1 GROUP BY LANG1)
NAME
-------------------RANDY
DANIEL
SOLOMON
ROSY
DIANA
STEWART
STEPHEN
ELIZABETH
ANITA
MAUREEN

SALARY
--------3800
2900
4400
3100
5000
3100
3800
2500
3100
5000

LANG1
-------------------TAMIL
ENGLISH
HINDI
LATIN
GREEK
ARABIC
TAMIL
URUDU
JAPANESE
FRENCH

10 rows selected.

SOLUTION 3.4
SQL> SELECT NAME,MONTHS_BETWEEN(SYSDATE,DOJ)/12 "YEARS OF
EXPERIENCE" FROM AUTHOR WHERE
MONTHS_BETWEEN(SYSDATE,DOJ)/12=
(SELECT MIN(MONTHS_BETWEEN(SYSDATE,DOJ)/12) FROM AUTHOR);
NAME
-------------------ELIZABETH
1 row selected.

YEARS OF EXPERIENCE
------------------.1035164

SOLUTION 3.5
SQL> SELECT NAME,MONTHS_BETWEEN(SYSDATE,DOJ)/12
"YEARS OF EXPERIENCE" FROM AUTHOR WHERE
MONTHS_BETWEEN(SYSDATE,DOJ)/12
=(SELECT MAX(MONTHS_BETWEEN(SYSDATE,DOJ)/12)
FROM AUTHOR WHERE SEX='M' AND (LANG1='TAMIL' OR
LANG2='TAMIL'));
NAME
-------------------LUKE

YEARS OF EXPERIENCE
------------------8.0874128

1 row selected.
SOLUTION 3.6
SQL> SELECT NAME,MONTHS_BETWEEN(SYSDATE,DOB)/12 "AGE"
FROM AUTHOR WHERE MONTHS_BETWEEN(SYSDATE,DOB)/12=
(SELECT MIN(MONTHS_BETWEEN(SYSDATE,DOB)/12) FROM AUTHOR
WHERE LANG1='LATIN' OR LANG2='LATIN');
NAME
-------------------ROSY

AGE
--------23.302285

1 row selected.

SOLUTION 3.7
SQL> SELECT NAME, SALARY,LANG1 "LANGUAGE1",LANG2
"LANGUAGE2" FROM AUTHOR WHERE SEX='F' AND SALARY > 3000
AND LANG1 NOT IN ('JAPANESE','GREEK', 'HINDI','LATIN') AND LANG2
NOT IN ('JAPANESE','GREEK', 'HINDI','LATIN');
NAME
SALARY
-------------------- --------LUCILLE
3500
1 row selected.

LANGUAGE1
-------------------TAMIL

LANGUAGE2
-------------------URUDU

SOLUTION 3.8
SQL> SELECT UNIVER,COUNT(NAME) "NO OF STUDENTS" FROM
STUDIES GROUP BY UNIVER HAVING COUNT(NAME)=(SELECT
MAX(COUNT(NAME)) FROM STUDIES GROUP BY UNIVER);
UNIVER
-------------------OXFORD

NO OF STUDENTS
-------------4

1 row selected.
SOLUTION 3.9
SQL> SELECT COURSE,COUNT(NAME) "NO OF STUDENTS" FROM
STUDIES GROUP BY COURSE HAVING COUNT(NAME)=(SELECT
MAX(COUNT(NAME)) FROM STUDIES GROUP BY COURSE);
COURSE
-------------------B.COM

NO OF STUDENTS
-------------4

1 row selected.
SOLUTION 3.10
SQL> SELECT UNIVER, COURSE, CCOST FROM STUDIES WHERE CCOST
< (SELECT AVG(CCOST) FROM STUDIES);
UNIVER
-------------------CAMBRIDGE
FLORIDA
BOMBAY
HARWARD
ALASKA
CALIFORNIA
SYDNEY
7 rows selected.

COURSE
-------------------B.COM
B.COM
B.COM
B.A
M.A
B.SC
B.COM

CCOST
--------15000
12000
15000
10000
30000
11000
14000

SOLUTION 3.11
SQL> SELECT COURSE FROM STUDIES WHERE CCOST=
(SELECT MAX(CCOST) FROM STUDIES);
COURSE
-------------------M.E
1 row selected.
SOLUTION 3.12
SQL> SELECT UNIVER FROM STUDIES WHERE CCOST=
(SELECT MAX(CCOST) FROM STUDIES);
UNIVER
-------------------HARWARD
1 row selected.
SOLUTION 3.13
SQL> SELECT COURSE FROM STUDIES GROUP BY COURSE
HAVING COUNT(NAME) < (SELECT AVG(COUNT(NAME)) FROM
STUDIES GROUP BY COURSE);
COURSE
-------------B.A
B.E
B.SC
M.A
M.COM
5 rows selected.

SOLUTION 3.14
SQL> SELECT DISTINCT(UNIVER) FROM STUDIES WHERE CCOST >
15000;
UNIVER
-------------------HARWARD
SYDNEY
ALASKA
OXFORD
4 rows selected.
SOLUTION 3.15
SQL> SELECT COURSE FROM STUDIES WHERE CCOST > (SELECT
AVG(CCOST)-5000 FROM STUDIES) AND CCOST < (SELECT
AVG(CCOST)+5000 FROM STUDIES);
COURSE
-------------M.COM
B.A
2 rows selected.
SOLUTION 3.16
SQL> SELECT TITLE FROM BOOK WHERE WCOST =(SELECT
MAX(WCOST) FROM BOOK);
TITLE
------------------------EXCISE POLICY
1 row selected.

SOLUTION 3.17
SQL> SELECT TITLE FROM BOOK WHERE BCOST =(SELECT
MIN(BCOST) FROM BOOK);
TITLE
------------------------SELF COOKING
1 row selected.
SOLUTION 3.18
SQL> SELECT NAME, TITLE, SOLD "NO OF COPIES" FROM BOOK
WHERE SOLD=(SELECT MIN(SOLD) FROM BOOK);
NAME
-------------------CATHARINE

TITLE
------------------------KNOW YOUR SALES TAX

NO OF COPIES
-----------15

1 row selected.
SOLUTION 3.19
SQL> SELECT WRI_IN "LANGUAGE" FROM BOOK
WHERE SOLD*BCOST=(SELECT MAX(SOLD*BCOST) FROM BOOK);
LANGUAGE
-------------------JAPANESE
1 row selected.
SOLUTION 3.20
SQL> SELECT SOLD "NO OF COPIES", TITLE FROM BOOK
WHERE BCOST-WCOST=(SELECT MIN(BCOST-WCOST) FROM BOOK);
NO OF COPIES
-----------20
1 row selected.

TITLE
------------------------DO IT YOURSELF

SOLUTION 3.21
SQL> SELECT TITLE,WCOST FROM BOOK WHERE WCOST=(SELECT
MAX(WCOST) FROM BOOK WHERE WRI_IN='TAMIL');
TITLE
------------------------CURRENT COMPUTERS
GRE ENTRANCE EXAMS

WCOST
--------300
300

2 rows selected.
SOLUTION 3.22
SQL> SELECT WRI_IN "LANGUAGE", COUNT(TITLE) "NO OF BOOKS"
FROM BOOK GROUP BY WRI_IN HAVING COUNT(TITLE)=
(SELECT MAX(COUNT(TITLE)) FROM BOOK GROUP BY WRI_IN);
LANGUAGE
-------------------TAMIL

NO OF BOOKS
----------4

1 row selected.
SOLUTION 3.23
SQL> SELECT NAME, COUNT(TITLE) "NO OF BOOKS"
FROM BOOK GROUP BY NAME HAVING COUNT(TITLE)=
(SELECT MAX(COUNT(TITLE)) FROM BOOK GROUP BY NAME);
NAME
-------------------DIANA

NO OF BOOKS
----------3

1 row selected.
SOLUTION 3.24
SQL> SELECT NAME FROM BOOK WHERE BCOST
= (SELECT MAX(BCOST) FROM BOOK);
NAME
-------------------ANITA
1 row selected.

SOLUTION 3.25
SQL> SELECT TITLE FROM BOOK WHERE SOLD <
(SELECT AVG(SOLD) FROM BOOK);
TITLE
------------------------SHORT STORIES
JAPANESE IN 30 DAYS
KNOW YOUR SALES TAX
BANKING
LEARN ARCHITECTURE
STATISTICS
EXCISE POLICY
PROGRAMMING IN C++
DO IT YOURSELF
PERSONALITY EVALUATOR
10 rows selected.
SOLUTION 3.26
SQL> SELECT NAME,WRI_IN,TITLE FROM BOOK X
WHERE WCOST =(SELECT MIN(WCOST) FROM BOOK WHERE
X.NAME=NAME AND X.WRI_IN=WRI_IN GROUP BY NAME,WRI_IN);
NAME
-------------------RANDY
RANDY
SOLOMON
SOLOMON
ROSY
CATHARINE
DIANA
DIANA
LUKE
STEWART
STEWART
STEPHEN
STEPHEN
ANITA
ANITA
LUCILLE
LUCILLE
MAUREEN
18 rows selected.

WRI_IN
-------------------URUDU
TAMIL
GERMAN
HINDI
LATIN
LATIN
HINDI
GREEK
TAMIL
ARABIC
JAPANESE
LATIN
TAMIL
JAPANESE
ARABIC
TAMIL
URUDU
JAPANESE

TITLE
--------------------GENERAL KNOWLEDGE
ACCOUNTING POLICY
SHORT STORIES
KNOW YOUR ENGLISH
JAPANESE IN 30 DAYS
KNOW YOUR SALES TAX
BANKING
LEARN ARCHITECTURE
STATISTICS
EXCISE POLICY
CURRENT COMPUTERS
PROGRAMMING IN C++
GRE ENTRANCE EXAMS
INTERIOR DECORATION
SELF COOKING
DO IT YOURSELF
PERSONALITY EVALUATOR
BEAUTY TIPS

SOLUTION 3.27
SQL> SELECT NAME, DOB FROM AUTHOR WHERE
DOB=(SELECT MAX(DOB) FROM AUTHOR WHERE
TO_CHAR(DOB,'YYYY')='1970' AND SEX='M');
NAME
-------------------SOLOMON

DOB
--------10-OCT-70

1 row selected.
SOLUTION 3.28
SQL> SELECT NAME,DOJ FROM AUTHOR WHERE
DOJ=(SELECT MIN(DOJ) FROM AUTHOR WHERE
SEX='F' AND TO_CHAR(DOJ,'YYYY')='1996');
NAME
-------------------DIANA

DOJ
--------06-AUG-96

1 row selected.
SOLUTION 3.29
SQL> SELECT TO_CHAR(DOB,'YYYY') "YEAR", COUNT(NAME) "NO OF
AUTHORS" FROM AUTHOR GROUP BY TO_CHAR(DOB,'YYYY') HAVING
COUNT(NAME)=(SELECT MAX(COUNT(NAME)) FROM AUTHOR GROUP
BY TO_CHAR(DOB,'YYYY'));

YEAR
----1970
1975

NO OF AUTHORS
------------3
3

2 rows selected.

SOLUTION 3.30
SQL> SELECT TO_CHAR(DOJ,'MONTH') "MONTH",COUNT(NAME)
"NO OF AUTHORS" FROM AUTHOR GROUP BY TO_CHAR(DOJ,'MONTH')
HAVING COUNT(NAME)=(SELECT MAX(COUNT(NAME)) FROM AUTHOR
GROUP BY TO_CHAR(DOJ,'MONTH'));
MONTH
---------APRIL

NO OF AUTHORS
------------4

1 row selected.
SOLUTION 3.31
SQL> SELECT NAME,SALARY FROM AUTHOR WHERE SEX='M' AND
SALARY (SELECT AVG(SALARY) FROM AUTHOR WHERE SEX='F');

NAME
-------------------BRAIN
LUKE
STEWART

SALARY
--------2500
2900
3100

3 rows selected.
SOLUTION 3.32
SQL> SELECT NAME, SALARY FROM AUTHOR WHERE SEX='F' AND
SALARY > (SELECT MAX(SALARY) FROM AUTHOR WHERE SEX='M');
NAME
-------------------DIANA
MAUREEN
2 rows selected.

SALARY
--------5000
5000

SOLUTION 3.33
SQL> SELECT LANG1 FROM AUTHOR GROUP BY LANG1
HAVING COUNT(LANG1)=(SELECT MAX(COUNT(LANG1)) FROM
AUTHOR GROUP BY LANG1);
LANG1
-------------------TAMIL
1 row selected.

LAB: SECTION 4
4.1. Display the details of those who are drawing the same salary as ANITA.
4.2. Display the details of books written by the authors earning more than 3500.
4.3. Display the details of the books written in TAMIL by female authors.
4.4. Display the details of those authors who joined before 1996.
4.5. Display the details of the books written in LATIN by female author of
HARWARD University.
4.6. Display the number of books, number of copies sold for each author,
university wise.
4.7. Display the details of the books written in LATIN by male authors, who
belong to the university in which most number of authors studied.
4.8. Display the details of the books written by the male authors born before
1970 and female authors born after 1974.
4.9. Display the details of the book that was written in the language that is not
the authors' first proficiency (lang 1).
4.10. Display the details of the book that was written in the language, which is
neither the first nor the second proficiency of the author.
4.11. Display the details of the book written by the male students who studied in
OXFORD University.
4.12. Display the names of authors who have not written any book.
4.13. What is the total written cost of the book written by the author(s) who has
(have) studied in ALASKA university?
4.14. Who are the authors who joined on their birthday?
4.15. Who are the authors who have the same lang2 as the lang1 of ROSY?
4.16. Display the total sales value of book, university wise.
4.17. In which university did the author who wrote the costliest book study?
Note - Costliest book is the one having maximum written cost.
4.18. Which language listed in lang 1 and lang 2 has not been used to write any
book ?

4. 19. How much does the person who wrote the highest selling book earn, and
where did he/she undergo the course?
4.20. Which is the book having maximum writing cost which is written by an
author with under 3 year experience?
4.21. What is the average salary for those whose book's sales value is more than
300?
4.22. How many books were written by students, who studied in the university
that charged the lowest course fee?
4.23. How many books were written by an author who wrote the book which
has the least writing cost and where did he/she study?
4.24. How many books were written by female authors earning more than the
highest paid male author?
4.25. How many books were written by the most experienced author
from SYDNEY university ?
4.26. List the authors (from the book table) and the universities they studied,
including those who have not written any book.
4.27. List the author names (from the author table) and the number of books
they have written, though they have not written any book.
4.28. List all the details of authors who have done a course at FLORIDA
university.
NOTE: Solutions are given at the end. However it is better that you
attempt the solution on your own and refer to the Solutions only in case of
doubt or to confirm the solution.

SOLUTIONS: SECTION 4
SOLUTION 4.1
SQL> SELECT NAME,SALARY,SEX,LANG1,LANG2 FROM AUTHOR
WHERE SALARY=(SELECT SALARY FROM AUTHOR WHERE
NAME='ANITA') AND NAME <> 'ANITA';
NAME
-------------------ROSY
STEWART

SALARY
-------3100
3100

S
-F
M

LANG1
-------------------LATIN
ARABIC

LANG2
------------------LATIN
JAPANESE

2 rows selected.
SOLUTION 4.2
SQL> SELECT BOOK.NAME, TITLE, WCOST, BCOST FROM
AUTHOR,BOOK
WHERE AUTHOR.NAME=BOOK.NAME AND SALARY > 3500;
NAME
-------------------DIANA
DIANA
DIANA
MAUREEN
RANDY
RANDY
SOLOMON
SOLOMON
STEPHEN
STEPHEN

TITLE
------------------------BANKING
LEARN ARCHITECTURE
ACCOUNTING POLICY
BEAUTY TIPS
GENERAL KNOWLEDGE
ACCOUNTING POLICY
SHORT STORIES
KNOW YOUR ENGLISH
PROGRAMMING IN C++
GRE ENTRANCE EXAMS

WCOST
--------150
225
250
120
250
200
400
100
250
300

BCOST
--------250
500
450
200
450
350
650
300
500
550

10 rows selected.
SOLUTION 4.3
SQL> SELECT BOOK.NAME, TITLE, WCOST, BCOST FROM AUTHOR,
BOOK WHERE AUTHOR.NAME=BOOK.NAME AND SEX='F' AND
WRI_IN='TAMIL';
NAME
-------------------LUCILLE

1 row selected.

TITLE
------------------------DO IT YOURSELF

WCOST
--------80

BCOST
--------125

SOLUTION 4.4
SQL> SELECT NAME, SEX, SALARY, DOJ FROM AUTHOR WHERE
TO_CHAR(DOJ,'YYYY') < 1996;
NAME
-------------------RANDY
DANIEL
SOLOMON
CATHARINE
BRAIN
LUKE
STEWART
STEPHEN
LUCILLE

S
-

F
M
M

SALARY
DOJ
--------- --------M
3800
12-APR-94
M
2900
21-MAR-92
M
4400
10-OCT-94
3000
05-JAN-95
2500
04-JUL-93
2900
11-APR-90
M
3100
19-APR-93
M
3800
18-SEP-94
F
3500
02-FEB-94

9 rows selected.
SOLUTION 4.5
SQL> SELECT TITLE, BOOK.NAME, WCOST, BCOST FROM AUTHOR,
BOOK, STUDIES WHERE AUTHOR.NAME=BOOK.NAME AND
AUTHOR.NAME=STUDIES.NAME AND SEX='F' AND WRI_IN='LATIN'
AND UNIVER='HARWARD';
TITLE
------------------------KNOW YOUR SALES TAX

1 row selected.

NAME
-------------------CATHARINE

WCOST
--------100

BCOST
--------200

SOLUTION 4.6
SQL> SELECT UNIVER, BOOK.NAME, COUNT(TITLE) "NO OF BOOKS",
SUM(SOLD) "TOTAL COPIES" FROM BOOK,STUDIES WHERE
BOOK.NAME = STUDIES.NAME GROUP BY UNIVER, BOOK.NAME
ORDER BY UNIVER;
UNIVER
-------------------HARWARD
HARWARD
SYDNEY
SYDNEY
ALASKA
OXFORD
OXFORD
OXFORD
OXFORD
FLORIDA
BOMBAY

NAME
-------------------CATHARINE
LUKE
MAUREEN
ANITA
STEWART
DIANA
LUCILLE
RANDY
STEPHEN
SOLOMON
ROSY

NO OF BOOKS
----------1
1
1
2
2
3
2
2
2
2
1

TOTAL COPIES
-----------15
30
40
130
75
90
50
100
80
75
25

11 rows selected.
SOLUTION 4.7
SQL> SELECT TITLE, WCOST, BCOST, BOOK.NAME "AUTHOR" FROM
BOOK, AUTHOR, STUDIES WHERE AUTHOR.NAME=BOOK.NAME AND
STUDIES.NAME=AUTHOR.NAME AND SEX='M' AND WRI_IN='LATIN'
AND UNIVER=(SELECT UNIVER FROM STUDIES GROUP BY UNIVER
HAVING COUNT(NAME)=(SELECT MAX(COUNT(NAME)) FROM STUDIES
GROUP BY UNIVER));
TITLE
------------------------PROGRAMMING IN C++

WCOST
--------250

BCOST
--------500

AUTHOR
-------------------STEPHEN

SOLUTION 4.8
SQL> SELECT BOOK.NAME, DOB "DATE OF BIRTH", TITLE, WCOST
FROM AUTHOR, BOOK WHERE BOOK.NAME=AUTHOR.NAME AND
((SEX='F' AND TO_CHAR(DOB,'YYYY')>1974)
OR (SEX='M' AND TO_CHAR(DOB,'YYYY')<1970));
NAME
-------------------MAUREEN
RANDY
RANDY
ROSY
STEWART
STEWART
LUKE

DATE OF B
--------03-DEC-75
12-APR-66
12-APR-66
25-JAN-75
28-AUG-65
28-AUG-65
30-NOV-65

TITLE
------------------------BEAUTY TIPS
GENERAL KNOWLEDGE
ACCOUNTING POLICY
JAPANESE IN 30 DAYS
EXCISE POLICY
CURRENT COMPUTERS
STATISTICS

WCOST
--------120
250
200
125
450
300
200

7 rows selected.
SOLUTION 4.9
SQL> SELECT TITLE, WRI_IN, WCOST, BCOST, BOOK.NAME "AUTHOR"
FROM BOOK, AUTHOR WHERE AUTHOR.NAME=BOOK.NAME AND
WRI_IN NOT IN(AUTHOR.LANG1);
TITLE
------------------------BANKING
PERSONALITY EVALUATOR
KNOW YOUR SALES TAX
BEAUTY TIPS
SELF COOKING
GENERAL KNOWLEDGE
CURRENT COMPUTERS
SHORT STORIES
PROGRAMMING IN C++

WRI_IN
-------------------HINDI
URUDU
LATIN
JAPANESE
ARABIC
URUDU
JAPANESE
GERMAN
LATIN

WCOST BCOST
--------- --------150
250
80
150
100
200
120
200
40
90
250
450
300
500
400
650
250
500

AUTHOR
-------DIANA
LUCILLE
CATHARINE
MAUREEN
ANITA
RANDY
STEWART
SOLOMON
STEPHEN

9 rows selected.
SOLUTION 4.10
SQL> SELECT BOOK.NAME, TITLE, WRI_IN FROM AUTHOR X,BOOK
WHERE X.NAME=BOOK.NAME AND WRI_IN NOT IN
(SELECT LANG1 FROM AUTHOR WHERE X.NAME=NAME)
AND WRI_IN NOT IN (SELECT LANG2 FROM AUTHOR WHERE
X.NAME=NAME);
No row selected.
(This is because the author writes a book only in his known language).

SOLUTION 4.11
SQL> SELECT TITLE, BOOK.NAME "AUTHOR", WCOST, SOLD FROM
AUTHOR, BOOK, STUDIES WHERE AUTHOR.NAME=BOOK.NAME AND
STUDIES.NAME=AUTHOR.NAME AND SEX='M' AND UNIVER='OXFORD';
TITLE
------------------------GENERAL KNOWLEDGE
ACCOUNTING POLICY
PROGRAMMING IN C++
GRE ENTRANCE EXAMS

AUTHOR
-------------------RANDY
RANDY
STEPHEN
STEPHEN

WCOST
--------250
200
250
300

SOLD
--------60
40
35
45

4 rows selected.
SOLUTION 4.12
SQL> SELECT NAME FROM AUTHOR WHERE NAME
NOT IN (SELECT NAME FROM BOOK);
NAME
-------------------DANIEL
BRAIN
ELIZABETH
3 rows selected.
SOLUTION 4.13
SQL> SELECT SUM(WCOST)"TOTAL COST" FROM BOOK,STUDIES
WHERE BOOK.NAME=STUDIES.NAME AND UNIVER='ALASKA';
TOTAL COST
------------------750
1 row selected.

SOLUTION 4.14
SQL> SELECT NAME, DOJ, DOB FROM AUTHOR WHERE
TO_CHAR(DOJ,'DD MONTH') =TO_CHAR(DOB,'DD MONTH');
NAME
-------------------RANDY
SOLOMON

DOJ
--------12-APR-94
10-OCT-94

DOB
--------12-APR-66
10-OCT-70

2 rows selected.
SOLUTION 4.15
SQL> SELECT NAME, LANG2 FROM AUTHOR WHERE LANG2
= (SELECT LANG1 FROM AUTHOR WHERE NAME='ROSY');
NAME
-------------------DANIEL
ELIZABETH

LANG2
-------------------LATIN
LATIN

2 rows selected.
SOLUTION 4.16
SQL> SELECT UNIVER, SUM(BCOST * SOLD) "TOTAL SALES VALUE"
FROM STUDIES, BOOK WHERE BOOK.NAME=STUDIES.NAME
GROUP BY UNIVER;
UNIVER
-------------------HARWARD
SYDNEY
ALASKA
OXFORD
FLORIDA
BOMBAY
6 rows selected.

TOTAL SALES VALUE


----------------13500
52700
40500
126750
34750
6250

SOLUTION 4.17
SQL> SELECT UNIVER FROM BOOK, STUDIES WHERE
BOOK.NAME=STUDIES.NAME AND WCOST=(SELECT MAX(WCOST)
FROM BOOK);
UNIVER
-------------------ALASKA
SOLUTION 4.18
SQL> (SELECT LANG1 FROM AUTHOR
UNION
SELECT LANG2 FROM AUTHOR)
MINUS
SELECT WRI_IN FROM BOOK;
LANG1
-------------------ENGLISH
FRENCH
2 rows selected.
SOLUTION 4.19
SQL> SELECT BOOK.NAME, UNIVER, SALARY FROM BOOK, STUDIES,
AUTHOR WHERE
BOOK.NAME=STUDIES.NAME AND AUTHOR.NAME = STUDIES.NAME
AND SOLD =(SELECT MAX(SOLD) FROM BOOK);
NAME
-------------------ANITA
1 row selected.

UNIVER
-------------------SYDNEY

SALARY
--------3100

SOLUTION 4.20
SQL> SELECT TITLE FROM BOOK WHERE
WCOST=(SELECT MAX(WCOST) FROM
BOOK, AUTHOR WHERE AUTHOR.NAME = BOOK.NAME AND
MONTHS_BETWEEN(DOJ,SYSDATE)/12 < 3);
TITLE
------------------------EXCISE POLICY
1 row selected.
SOLUTION 4.21
SQL> SELECT AVG(SALARY) "AVERAGE SALARY" FROM AUTHOR,BOOK
WHERE BOOK.NAME=AUTHOR.NAME AND BCOST > 300;
AVERAGE SALARY
-------------3800
1 row selected.
SOLUTION 4.22
SQL> SELECT COUNT(TITLE) "NO OF BOOKS" FROM BOOK,STUDIES
WHERE BOOK.NAME=STUDIES.NAME AND UNIVER=(SELECT UNIVER
FROM STUDIES WHERE CCOST=(SELECT MIN(CCOST) FROM
STUDIES));
NO OF BOOKS
----------2
1 row selected.

SOLUTION 4.23
SQL> SELECT UNIVER, COUNT(TITLE) "NO OF BOOKS" FROM
BOOK,STUDIES WHERE BOOK.NAME=STUDIES.NAME AND
WCOST=(SELECT MIN(WCOST) FROM BOOK) GROUP BY UNIVER;
UNIVER
-------------------SYDNEY

NO OF BOOKS
----------1

1 row selected.
SOLUTION 4.24
SQL> SELECT COUNT(TITLE) "NO OF BOOKS" FROM BOOK,AUTHOR
WHERE BOOK.NAME=AUTHOR.NAME AND SEX='F' AND SALARY >
ALL(SELECT SALARY FROM AUTHOR WHERE SEX='M');
NO OF BOOKS
---------------------4
1 row selected.
SOLUTION 4.25
SQL> SELECT COUNT(TITLE) "NO OF BOOKS" FROM AUTHOR, BOOK,
STUDIES WHERE BOOK.NAME=STUDIES.NAME AND
AUTHOR.NAME=BOOK.NAME
AND MONTHS_BETWEEN(SYSDATE,DOJ)=(SELECT
MAX(MONTHS_BETWEEN(SYSDATE,DOJ)) FROM AUTHOR,STUDIES
WHERE AUTHOR.NAME=STUDIES.NAME AND UNIVER='SYDNEY');
NO OF BOOKS
---------------------1
1 row selected.

SOLUTION 4.26
SQL> SELECT DISTINCT(STUDIES.NAME), UNIVER FROM BOOK,
STUDIES WHERE BOOK.NAME(+)=STUDIES.NAME;
NAME
-------------------BRAIN
DIANA
LUCILLE
CATHARINE
MAUREEN
ANITA
RANDY
DANIEL
ELIZABETH
ROSY
STEWART
SOLOMON
LUKE
STEPHEN
14 rows selected.

UNIVER
-------------------HARWARD
OXFORD
OXFORD
HARWARD
SYDNEY
SYDNEY
OXFORD
CAMBRIDGE
CALIFORNIA
BOMBAY
ALASKA
FLORIDA
HARWARD
OXFORD

SOLUTION 4.27
SQL> SELECT AUTHOR.NAME, COUNT(BOOK.NAME) "NO OF BOOKS"
FROM BOOK, AUTHOR WHERE
AUTHOR.NAME = BOOK.NAME(+) GROUP BY AUTHOR.NAME;
NAME
-------------------BRAIN
DIANA
LUCILLE
CATHARINE
MAUREEN
ANITA
RANDY
DANIEL
ELIZABETH
ROSY
STEWART
SOLOMON
LUKE
STEPHEN
14 rows selected.

NO OF BOOKS
----------0
3
2
1
1
2
2
0
0
1
2
2
1
2

SOLUTION 4.28
SQL> SELECT AUTHOR.NAME, SEX, SALARY, CCOST FROM AUTHOR,
STUDIES WHERE AUTHOR.NAME=STUDIES.NAME AND
UNIVER LIKE 'FLORIDA%';
NAME
-------------------SOLOMON
1 row selected.

S
-M

SALARY
--------4400

CCOST
--------12000

More Database Objects


Objectives
In this session, you will learn about Views, Synonyms, Sequences and Indexes.

Topics

Views
The Create View Command
View of more than one table
Views based on Arithmetic Expressions
Synonyms
Sequences
Indexes

Views
A view is like a window through which one can view or change information in
tables. It is derived from one or more tables. There are two main reasons to use
views:
1. Security: As a personnel manager of the company in the sample company,
one may want the other employees to have access to the most of the
information, but not to the salary column. In that case a view, which is derived
from EMP table neglecting the salary column, can be given to them.
2. Convenience: Instead of using a complex query to get information, you can
create a view, which permits you to get the same information by simple query.

The CREATE VIEW command


A view can be created using the CREATE VIEW command.
Syntax: CREATE VIEW user.view_name alias,alias,... AS {QUERY} [WITH
CHECK OPTION]
The WITH CHECK OPTION constraint specifies, whether the value inserted
and updated through view will satisfy the query criteria in defining the view.
The view created from the single table can be treated as a table.
For example, to create a view, which contains dept 10 information only, enter:
SQL> CREATE VIEW EMP10 (EMPNO, ENAME, SAL, COMM) AS SELECT
EMPNO, ENAME, SAL, COMM FROM EMP WHERE DEPTNO=10;
The view can be queried as a table. To get the information through the view,
type:
SQL> SELECT * FROM EMP10;
One can also use a WHERE clause in querying a view. Any changes done on
the table is reflected in the view. For example, change the department of Steve
to 10, and view the change through view.
SQL> UPDATE EMP SET DEPTNO=20 WHERE ENAME='STEVE';
SQL> SELECT * FROM EMP10;
Note that deleting rows through view is possible only when the view contains
the primary key of the base table. Also, insertion through view is possible only
when the other columns which are not part of the view, can accept null values.

Views of more than one table


Joining any number of tables in a view is possible. Suppose one wants to create
a view projects that contains project names, employee names, employee
numbers and locations. This information is scattered among the EMP, DEPT
and PROJ tables. Remember that one cannot UPDATE, INSERT or DELETE
through a view that selects from more than one table.
Example: To create a PROJECTS view containing columns from EMP, DEPT
and PROJ tables, enter:
SQL> CREATE VIEW PROJECTS(PROJECT,EMPLOYEE,
EMP_NUMBER,LOCATION) AS SELECT PNAME, ENAME, EMPNO, LOC
FROM PROJ,EMP,DEPT WHERE EMP.DEPTNO=DEPT.DEPTNO AND
EMP.PROJNO=PROJ.PROJNO;
To list the projects and employees in London, enter:
SQL> SELECT PROJECT, EMPLOYEE, LOCATION FROM PROJECTS
WHERE LOCATION='London';

Views based on arithmetic expressions


One can include an arithmetic expression the query clause of a view. Suppose
we want to define a view named PAY, which calculates the employee's annual
salary, we need to enter:
SQL> CREATE VIEW PAY (NAME, MONTHLY_SAL, ANNUAL_SAL,
DEPTNO) AS SELECT ENAME, SAL, SAL*12,DEPTNO FROM EMP;
You can select from the view to see the virtual column ANNUAL_SAL.
SQL> SELECT * FROM PAY WHERE DEPTNO=30;
One can drop a view as if it were a table.
SQL> DROP VIEW PAY;

Synonyms
A synonym is a database object, which represents a table with different name.
To define a synonym for the table, the CREATE SYNONYM command is used.
The synonym name can be used instead of table name.
Syntax: CREATE [PUBLIC] SYNONYM {user.synonym_name} FOR
{user.table};
The optional word PUBLIC specifies that the synonym be accessible by all
users. If omitted, the synonym is private, accessible only by the synonym's
creator. Only a DBA can create a PUBLIC synonym.
To create a synonym S_DEPT for SCOTT's EMP table, enter:
SQL> CREATE SYNONYM S_DEPT FOR SCOTT.DEPT;
Now one can query SCOTT's DEPT using the synonym S_DEPT;
SQL> SELECT * FROM S_DEPT;

Sequences
A sequence is a database object, which can be initialized to generate unique
integers. It can be created using the CREATE SEQUENCE command.
Syntax: CREATE SEQUENCE {user.sequence_name} INCREMENT BY n
START WITH n MAXVALUE n | NOMAXVALUE MINVALUE n |
NOMINVALUE CYCLE | NOCYCLE CACHE 20 |n| NOCACHE
This command sets up an ORACLE object from which users can generate
unique integers. You can use this unique numbers to generate primary key
values automatically.
INCREMENT BY n sets the interval between sequence numbers.
START WITH n sets the first sequence number to be created. The default for an
ascending sequence is MINVALUE; for descending sequence is MAXVALUE.
MAXVALUE n | NOMAXVALUE is the largest number the sequence will
generate. The default is 10e27-1 for an ascending sequence, 1 for a descending
sequence.
CYCLE | NOCYCLE If CYCLE, the sequence goes to MINVALUE after
reaching MAXVALUE for ascending sequence, or to MAXVALUE after
reaching MINVALUE for descending sequences. If NOCYCLE (default), no
numbers will be generated after the end of the sequence is reached.

CACHE n | NOCACHE CASHE per-allocates sequence numbers so they may


be kept in memory to improve generation speed. The CACHE value must be
less than MAXVALUE minus MINVALUE. The default is CACHE 20.
For example, to create a sequence that starts with 1, increases by 1, maximum
value is 1000, enter:
SQL> CREATE SEQUENCE EMPNO_SEQ INCREMENT BY 1 START WITH
1 MAXVALUE 1000;
Having created this sequence, we can use this in the INSERT command for
generating the empno automatically. The following command shows this.
SQL> INSERT INTO EMP(EMPNO,ENAME,DEPTNO,SAL) VALUES
( empno_seq.nextval,'LUCY',20,3800);
Note that every time sequence_name.currval is invoked a new number will be
generated.
Similarly, we can get the current value of the sequence by using
sequence_name.currval.
One can alter the sequence using the ALTER SEQUENCE command.
SQL> ALTER SEQUENCE EMPNO_SEQ INCREMENT BY 2;
Will make the sequence to generate in steps of 2.

To drop the sequence, issue the DROP SEQUENCE command.


SQL> DROP SEQUENCE EMPNO_SEQ;
Will remove the sequence from the database.

Indexes
Index is another database object that can be created on one or more columns in
a table, and it acts like an index to a table to reduce the access time. To create an
index, use the following syntax:
Syntax: CREATE [UNIQUE] INDEX {index_name} ON table
{column1,column2,..};
An index may contain up to 16 columns. The optional key word UNIQUE
ensures that, no indexed columns have duplicate values in the table. ORACLE
automatically creates an UNIQUE index on a primary key or unique key
column.
For example, to create an index on the salary column of emp table, enter:
SQL> CREATE INDEX SAL_INDEX ON EMP(SAL);
One can drop the index if one wishes. The following command will remove the
above index from the database.
SQL> DROP INDEX SAL_INDEX;

LAB Exercises on Views, Synonyms and Indexes


Objectives
This is a LAB session on Views, Synonyms and Indexes. (Use the Authors,
Books and Studies Table of the Publishing Company).

Topics

Section I - Views
Solutions Section I - Views
Section II - Synonyms
Solutions Section II - Synonyms
Section III - Indexes
Solutions Section III - Indexes

SECTION 1 VIEWS
1.1. Create a view that contains the information about name of the author, his
salary and the university where he studied.
1.2. Get the information of authors through the view.
1.3. Create a view that contains the information of average, minimum,
maximum, total selling cost for each language.
1.4.Get the details of the language statistics through the view.
1.5.Create a view that contains the information of number of books written in
each language.
1.6.Get the information of no. of books through the view.
1.7.Create a view that contains the information of TAMIL authors.
1.8.Get the information of all TAMIL authors.
1.9. Insert a new author through the view whose first language is JAPANESE
and second language is HINDI.
1.10. Delete all the rows from the book_count view.
1.11. Remove the book_count view from the database.
NOTE: Solutions are given at the end. However it is better that you
attempt the solution on your own and refer to the Solutions only in case of
doubt or to confirm the solution.

SOLUTIONS: SECTION 1 - VIEWS


SOLUTION 1.1
SQL> CREATE VIEW AUTHOR_UNIVER (NAME, SALARY,
UNIVERSITY) AS SELECT AUTHOR.NAME, SALARY, UNIVER FROM
AUTHOR, STUDIES WHERE AUTHOR.NAME=STUDIES.NAME;
View created.

SOLUTION 1.2
SQL> SELECT * FROM AUTHOR_UNIVER;
NAME
-------------------BRAIN
DIANA
LUCILLE
CATHARINE
MAUREEN
ANITA
RANDY
DANIEL
ELIZABETH
ROSY
STEWART
SOLOMON
LUKE
STEPHEN

SALARY
--------2500
5000
3500
3000
5000
3100
3800
2900
2500
3100
3100
4400
2900
3800

UNIVERSITY
-------------------HARWARD
OXFORD
OXFORD
HARWARD
SYDNEY
SYDNEY
OXFORD
CAMBRIDGE
CALIFORNIA
BOMBAY
ALASKA
FLORIDA
HARWARD
OXFORD

14 rows selected.

SOLUTION 1.3
SQL> CREATE VIEW LANG_STAT(LANG, LOWCOST, MIDCOST,
HIGHCOST,TOTCOST) AS SELECT
WRI_IN,MIN(BCOST),AVG(BCOST),MAX(BCOST),
SUM(BCOST) FROM BOOK GROUP BY WRI_IN;
View created.

SOLUTION 1.4
SQL> SELECT * FROM LANG_STAT;
LANG

LOWCOST

MIDCOST

HIGHCOST

TOTCOST

-------------------HINDI
LATIN
JAPANESE
GERMAN
GREEK
ARABIC
TAMIL
LATIN
URUDU

------250
200
200
650
450
90
125
250
150

--------275
350
483.33333
650
475
345
343.75
250
300

--------300
500
750
650
500
600
550
250
450

--------550
700
1450
650
950
690
1375
250
600

9 rows selected.

SOLUTION 1.5
SQL> CREATE VIEW BOOK_COUNT(LANGUAGE,NO_OF_BOOKS)
AS SELECT WRI_IN,COUNT(*) FROM BOOK GROUP BY WRI_IN;
View created.

SOLUTION 1.6
SQL> SELECT * FROM BOOK_COUNT;
LANGUAGE
-------------------HINDI
LATIN
JAPANESE
GERMAN
GREEK
ARABIC
TAMIL
LATIN
URUDU

NO_OF_BOOKS
----------2
2
3
1
2
2
4
1
2

9 rows selected.

SOLUTION 1.7
SQL> CREATE VIEW
TAMIL_AUTHORS(NAME,DOB,DOJ,SEX,LANG1,LANG2,SALARY)

AS SELECT NAME,DOB,DOJ,SEX,LANG1,LANG2,SALARY FROM


AUTHOR
WHERE LANG1='TAMIL' OR LANG2='TAMIL' WITH CHECK
OPTION;
View created.

SOLUTION 1.8
SQL> SELECT * FROM TAMIL_AUTHORS;
NAME
------RANDY
LUKE
STEPHEN
LUCILLE

DOB
--------12-APR-66
30-NOV-65
20-JUL-72
02-DEC-69

DOJ
--------12-APR-94
11-APR-90
18-SEP-94
02-FEB-94

S
M
M
M
F

LANG1
------TAMIL
TAMIL
TAMIL
TAMIL

LANG2 SALARY
--------------URUDU 3800
ENGLISH 2900
LATIN
3800
URUDU 3500

4 rows selected.

SOLUTION 1.9
SQL> INSERT INTO TAMIL_AUTHORS VALUES ('RAGAVAN','12APR-67',SYSDATE,'M','JAPANESE','HINDI',4000);
ORA-01402: view WITH CHECK OPTION where-clause violation
(This error is due to the reason that the insertion should satisfy the
query criteria of the view that defines the view, which has been created
with WITH CHECK OPTION clause).

SOLUTION 1.10
SQL> DELETE BOOK_COUNT;
ORA-01732: data manipulation operation not legal on this view
(This is because the query which defines the view has arithmetic
expressions or functions).

SOLUTION 1.11
SQL> DROP VIEW BOOK_COUNT;
View dropped.

SECTION 2 - SYNONYMS
2.1 Create a synonym for the book table.
2.2 Use this synonym for viewing the information about authors and books
written by them.
2.3 Create a public synonym for the author table.
2.4 Drop the synonym, which was created for the book table.
NOTE: Solutions are given at the end. However it is better that you
attempt the solution on your own and refer to the Solutions only in case of
doubt or to confirm the solution.

SOLUTIONS: SECTION 2 - SYNONYMS


SOLUTION 2.1
SQL> CREATE SYNONYM BK FOR BOOK;
Synonym created.

SOLUTION 2.2
SQL> SELECT NAME, TITLE, WRI_IN "LANGUAGE" FROM BK;
NAME
-------------------RANDY
RANDY
SOLOMON
SOLOMON
ROSY
CATHARINE
DIANA
DIANA
DIANA
LUKE
STEWART
STEWART
STEPHEN
STEPHEN
ANITA
ANITA
LUCILLE
LUCILLE
MAUREEN

TITLE
------------------------GENERAL KNOWLEDGE
ACCOUNTING POLICY
SHORT STORIES
KNOW YOUR ENGLISH
JAPANESE IN 30 DAYS
KNOW YOUR SALES TAX
BANKING
LEARN ARCHITECTURE
ACCOUNTING POLICY
STATISTICS
EXCISE POLICY
CURRENT COMPUTERS
PROGRAMMING IN C++
GRE ENTRANCE EXAMS
INTERIOR DECORATION
SELF COOKING
DO IT YOURSELF
PERSONALITY EVALUATOR
BEAUTY TIPS

LANGUAGE
-------------------URUDU
TAMIL
GERMAN
HINDI
LATIN
LATIN
HINDI
GREEK
GREEK
TAMIL
ARABIC
JAPANESE
LATIN
TAMIL
JAPANESE
ARABIC
TAMIL
URUDU
JAPANESE

19 rows selected.

SOLUTION 2.3
SQL> CREATE PUBLIC SYNONYM AUT FOR AUTHOR;
ERROR
ORA-01031: insufficient privileges
(This error is due to the fact that, only the DBA can create a public
Synonym which can be accessed by all users.)

SOLUTION 2.4
SQL> DROP SYNONYM BK;
Synonym dropped.

LAB: SECTION 3 - INDEXES


3.1 Create an index on the salary column of the author table.
3.2 Create a unique index on the name column of the author table to ensure that
no two authors have the same name.
3.3 Drop the index created above.
NOTE: Solutions are given at the end. However it is better that you
attempt the solution on your own and refer to the Solutions only in case of
doubt or to confirm the solution.

SOLUTIONS: SECTION 3 - INDEXES


SOLUTION 3.1
SQL> CREATE INDEX sal_index ON author(salary);
Index created.

SOLUTION 3.2
SQL> CREATE UNIQUE INDEX unique_name ON author(name);
Index created.

SOLUTION 3.3
SQL> DROP INDEX unique_name;
Index dropped.

Transaction Control Commands and SQL*Plus


Formatting Commands
Objectives
In this session, you will learn about the COMMIT, ROLLBACK and SAVEPOINT
Commands. Also you will learn about SQL*Plus Formatting Commands.

Topics

Transaction
The COMMIT Command
The ROLLBACK Command
The SAVEPOINT Command
SQL*Plus Formatting Commands

Transaction
A transaction can be defined as a logical unit of work. A transaction is not made
permanent in ORACLE unless it is committed.
Controlling the Changes
Insertions and other changes to table normally are not committed (made
permanent) until you exit from SQL*PLUS normally, or until you execute
ALTER, AUDIT, CREATE, DISCONNECT, DROP, EXIT, GRANT,
NOAUDIT, QUIT or REVOKE commands.
Effects of non-committed transactions are:

You can see them when you query your tables, but
Other users cannot see them when they query your tables,
You can undo the transaction.

The COMMIT Command


Commit command is used to end a transaction and to make the changes
permanent to the database. The commit also releases the save-points in the
transaction and releases the transaction locks.
Syntax: COMMIT [WORK]; or COMMIT;
SQL> COMMIT;
The commit command forces SQL*PLUS to commit pending table changes to
the database. It is a good practice to commit the changes to the database as soon
as you finish a task. This will protect you against losing too much work if your
computer fails for some reason, or if the power goes off.

The ROLLBACK Command


The ROLLBACK command undoes the work in the current transaction, which
is left uncommitted.
Syntax: ROLLBACK [WORK] [TO] [SAVEPOINT][savepoint_id];
The word WORK is optional. If one wants to rollback the entire transaction, one
has to issue:
SQL> ROLLBACK;
There may be situations, where one wants to rollback only a part of transaction.
In that case, one has to rollback to a particular savepoint, which was used to
mark that transaction.
SQL> ROLLBACK TO insert_save;
Note: Once the changes are committed you can not rollback.

The SAVEPOINT Command


Savepoint is used to mark a transaction. Identifying the savepoint id, one can
later rollback to that particular savepoint, so that only a part of transaction will
be rolled back.
Syntax: SAVEPOINT {savepoint_id}
SQL> SAVEPOINT insert_save;
Saves the current transaction to the point insert_save.
Note: The commit command releases all the savepoint ids.

SQL*PLUS Formatting Commands


SQL*PLUS is usually thought of as a kind of interactive report writer. It uses
SQL to get information from the ORACLE database, and lets you create a wellformatted report by giving you easy control over titles, column headings,
subtotals and totals.
Some of the SQL*PLUS commands and their uses are discussed below.

Command
Ttitle [left] {text} right {text} [center]
{text}
Btitle [left] {text} right {text} [center]
{text}
Skip {number}

Description
Sets the top title for each page of the
report.
Sets the bottom title for each page of the
report.
Skips as many blank lines.

Set pause { on | off }

Makes the screen display stop or not stop


between pages of report depending on ON
or OFF.
Gives SQL*PLUS a variety of instructions
on the heading, format and treatment of
the column.
Displays the page number.
Tells SQL*PLUS where to put spaces
between the sections of report.
Makes the SQL*PLUS to calculate sub
totals.

Column {col_name} [format] {format


instructions} [justify] { justification}
[heading] {text}
SQL.pno
Break on {column}
Compute sum of {column} on {column}

Example: To create a product wise sales report that displays product no,
description, unit of measure, quantity, rate and total value, open the notepad
editor and enter the following code.

ttitle left 'Page No:' format 99 sql.pno center 'PRODUCTWISE SALES ' skip 4
btitle center 'COMPANY CONFIDENTIAL'
set pause on
column product_no format a15 justify center
column product_no heading 'Product Number'
column description heading 'Description'
column description format a25 justify center
column unit_measure heading 'UOM'
column qty_ordered justify right
column sell_price heading 'Rate'
SELECT
product_master.product_no,description,unit_measure,sum(qty_ordered)
"Quantity", sell_price,sum(qty_ordered) * sell_price "Total" FROM
sales_order_deatils,product_master WHERE
sales_order_details.product_no=product_master.product_no GROUP BY
product_master.product_no,description,unit_measure,sell_price;

Save the above with a file name, and run that file using start command. See the
format of the displayed report.

Introduction to PL/SQL
Objectives
In this session, you will learn about the relation between SQL and PL/SQL and the
advantages of PL/SQL. You will also learn about Conditional Control, Loop
Statements and how to display the user messages on screen.

Topics

Relation between SQL and PL/SQL


Advantages of PL/SQL
A Simple PL/SQL Block
Declaration using attributes
Loop Statements
Displaying the user messages on screen

Relation between SQL and PL/SQL


PL/SQL is an extension to SQL. PL/SQL lets you use all the SQL data
manipulation statements including INSERT, UPDATE, DELETE and SELECT
as well as the transaction processing statements COMMIT, ROLLBACK and
SAVEPOINT.
PL/SQL blocks can contain any number of SQL statements combined with the
following:

Flow of control statements such as IF ... THEN .... ELSE, EXIT and
GOTO
Repetition statements such as FOR....LOOP, WHILE...LOOP
Assignment statements such as X: = Y+Z. Unlike SQL, PL/SQL
allows you to logically group a set of statements and send them to the
RDBMS as a single block.

Advantages of PL/SQL
PL/SQL is a completely portable, high performance transaction processing
language that gives you more and better ways to express problems and design
database applications. Specifically, PL/SQL provides the following advantages:

Procedural capabilities
Improved performance
Enhanced productivity
Portability
Integration with RDBMS.

Procedural Capabilities
PL/SQL is a transaction processing language that offers procedural solutions.
You can use many of the constructs (loops, branches, assignments etc.) found in
traditional programming languages. It supports variable declarations, constant
declarations, error handling and usage of functions.

Improved performance
Without PL/SQL, the ORACLE RDBMS must process SQL statements one at a
time. Each SQL statement results in another call to be RDBMS and a higher
performance overhead. This overhead can become significant when you are
issuing many SQL statements in a networked environment. Each time a SQL
statement is issued, it must be sent over the network, creating a network traffic.
However with PL/SQL the entire block of statements can be sent only once to
RDBMS, thereby reducing the processing time.

Enhanced productivity
PL/SQL also brings added functionality to non procedural tools such as
SQL*FORMS. With PL/SQL in these tools, software developers can use
familiar procedural language constructs to develop applications. For example,
developers using SQL*FORMS can enter an entire PL/SQL block as a single
trigger. Thus, productivity is enhanced by, putting better tools in the hands of
developers. Furthermore, PL/SQL is the same in all environments. So, as soon
as developers master PL/SQL with one tool, they can boost productivity using
all the Oracle tools that support PL/SQL.

Portability
Applications written in PL/SQL are portable to any computer hardware
and operating system environment running the ORACLE V 6.0, 7.0
RDBMS.

Integration with RDBMS


Both PL/SQL and SQL have their foundations in SQL. Also, most PL/SQL
variables have datatypes, native to the RDBMS data dictionary.

A Simple PL/SQL Block


A simple PL/SQL block will have the following general structure:
DECLARE
{declaration of variables}
BEGIN
...........
sequence of statements including DML and TCL commands;
............
EXCEPTION
................
handle the errors here
.................
END;
In the DECLARE part of the above block we declare the variables, which are
used within the BEGIN and END block. For example, if one wants to declare a
variable, named "bonus" that can hold 7 digits, 2 of which are for decimal
points, and another variable named "in_stock" which is either TRUE or FALSE,
then one has to declare as follows:
DECLARE
bonus NUMBER (7,2);
in_stock BOOLEAN;

Declaration using attributes


PL/SQL objects (such as variables and constants) and database objects (such as
columns and tables) are associated with certain attributes. You can use these
attributes to simplify variable and constant declarations.

%TYPE attribute
The %TYPE attribute provides the datatype of a variable, constant or column.
This is particularly useful when declaring a variable that refers to a column in a
database table. For example, suppose one wants to declare a variable, which is
going to have a value of the EMPNO column of the EMP table. In this case, if
one does not know the exact datatype of EMPNO, one can declare the variable
as follows:
dummy_emp_no EMP.EMPNO%TYPE;

%ROWTYPE attribute
The %ROWTYPE attribute is useful if one wants to declare a record variable
that has the same structure as a row in a table or view, or as a row fetched from
a cursor.

Conditional Control
The IF statement lets you control whether or not a sequence of statements is
executed. In PL/SQL we can achieve conditional control by using IF, THEN,
ELSIF and ELSE clauses. The IF clauses lets you check a condition; the THEN
clause defines what to do if the condition is TRUE, and the optional ELSE or
ELSIF clause define what to do if the condition is FALSE.
Format:

IF [conditon] THEN
..........
..........
statements;
...........
ELSE
..........
statements;
.........
...........
END IF;

IF[condition] THEN
.........
statements;
..........
ELSIF [condition] THEN
............
statements;
................
................
END IF;

For example, to process bank transactions, every time a request for a withdrawal
is made, you might check to see if there are sufficient funds in the account to
cover the withdrawal. If funds are available, you debit account no. 3 by $ 500.
Else you do not. The can be done as follows:
DECLARE
acct_bal NUMBER(11,2);
BEGIN
SELECT bal INTO acct_bal FROM accounts WHERE acct_id=3;
IF acct_bal >=500 THEN
UPDATE accounts SET bal = bal - 500 WHERE acct_id=3;
ELSE
INSERT INTO temp VALUES(3,acct_bal,'Insufficient funds');
END IF;
END;

Loop Statements
A loop repeats a sequence of statements. You place the keyword LOOP
immediately before the first statement in the sequence of statements that you
want to repeat, and the keywords END LOOP immediately after the last
statement in the sequence. The following example shows the simplest loop:

LOOP
cntr:=cntr+1;
IF cntr >= 100 THEN
EXIT;
END IF;
END LOOP;

FOR loops
With a FOR loop, you can determine the number of times the loop has to be
executed.
Format:

FOR counter_variable IN [REVERSE] initial_value ..


last_value
LOOP
........
statements;
........
END LOOP;

The optional word REVERSE specifies, whether the counting should be made
in the ascending or descending order, with respect to the initial and the last
values.
For example, to count the numbers from 1 to 100 and insert their squares into
the SQUARE table,
Write a PL/SQL block as follows:
DECLARE
cntr NUMBER(3);
BEGIN
FOR cntr IN 1..100
LOOP
INSERT INTO square VALUES (cntr,cntr*cntr);
END LOOP;
COMMIT;
END;

WHILE loops
WHILE loop is similar to FOR loop, but unlike FOR loop it explicitly checks
for the condition.
Format:

WHILE {condition}
LOOP
.........
statements;
.........
END LOOP;

The above example can be done using a WHILE loop as follows:


DECLARE
cntr NUMBER(3):=1;
BEGIN
WHILE cntr<=100
LOOP
INSERT INTO square VALUES (cntr,cntr*cntr);
cntr:=cntr+1;
END LOOP;
COMMIT;
END;

Displaying the User Messages on the Screen


Any programming language requires a method through which messages can be
displayed to the user. DBMS_OUTPUT is a package that includes a number of
procedures and functions that accumulate information in a buffer so that they
can be retrieved later. These functions can also be used to display messages to
the user. PUT_LINE puts a piece of information in the buffer followed by an
end-of-line marker. It can also be used to display message to the user.
PUT_LINE accepts arguments of only character data type.
To display messages on the screen, use the SQL*PLUS environment parameter
SERVEROUTPUT that displays the information passed through PUT_LINE
function. The SERVEROUTPUT has to be SET to ON, using the command
SQL> SET SERVEROUTPUT ON
For example, to display a message to the user, write the following code within
the PL/SQL block:
DBMS_OUTPUT.PUT_LINE(' This is the message for you ');

Cursors and Error Handling


Objectives
In this Chapter, you will learn about Cursors and Error Handling in PL/SQL.

Topics

Cursors
Using the Explicit Cursors
Explicit Cursor Attributes
Implicit Cursor Attributes
Example of an Explicit Cursor and Attribute
Error handling in PL/SQL

Cursors
To process the SQL statements, PL/SQL opens a work area called a context
area. PL/SQL uses the context area to execute the SQL statement and store
processing information.
A PL/SQL construct called a cursor lets you name a context area, access its
stored information, and in some cases, control its processing. PL/SQL uses two
types of cursors.

Explicit Cursors
You can explicitly obtain a cursor for multi-row queries. (In most cases, you
can use a cursor FOR loop).

Implicit Cursors
PL/SQL implicitly obtains a cursor for all other SQL statements.
The set of rows returned by the query can consist of zero, one, or many rows,
depending on the number of rows that meet the query criteria. When a query
returns multiple rows, you can explicitly define a cursor to:

Process beyond the first row returned by the query,


Keep track of which row is currently processed

Imagine the set or rows being returned to a terminal screen. A screen cursor
could point to the first row to be processed, then the next row, and so on. In the
same way, a cursor identifies the current row in the set of rows returned by the
query. This allows PL/SQL to process the rows one at a time.

Using the Explicit cursors


If a query returns multiple rows, you can define an explicit cursor to keep track
of which row is being processed. You define the cursor in the declarative part of
your PL/SQL block by naming it and specifying a query. Then you use three
statements to manipulate the cursor: OPEN, FETCH and CLOSE.

Declaring a cursor
When you declare a cursor, you name it and associate it with a particular query.
In the following example, you declare a cursor named emp_cursor.
DECLARE
CURSOR emp_cursor IS SELECT ename,deptno FROM emp WHERE
sal>2000;
BEGIN
......

Opening a cursor
Opening a cursor executes the SELECT statement and identifies the active set
(all columns and rows that meet the query specifications and search criteria). An
example of the OPEN statement is:
OPEN emp_cursor;

Fetching with a cursor


The FETCH statement retrieves each row in the active set, one at a time. Each
time FETCH is executed, the cursor advances to the next row in the active set.
An example of the
FETCH statement is:
FETCH emp_cursor INTO emp_name,dept_num;

Closing a cursor
The CLOSE statement disables the cursor; the active set becomes undefined.
An example of the CLOSE statement is:
CLOSE emp_cursor;
PL/SQL releases all child cursors, including UNCLOSED explicit cursors,
when the parent cursor is closed.

Explicit Cursor Attributes


Explicit cursor has four attributes you can use to access the cursor's context
area:
%NOTFOUND, %FOUND, %ROWCOUNT and %ISOPEN. This means you
can get information about the execution of multi-row queries. To use an
attribute, simply append it to the name of the cursor.

Using %NOTFOUND
%NOTFOUND evaluates to TRUE if the last FETCH failed because no more
rows were available, or to FALSE if the last FETCH returned a row. The
following example uses %NOTFOUND to exit a loop.
LOOP
FETCH emp_cursor INTO emp_name,dept_num;
EXIT WHEN emp_cursor%NOTFOUND;
.............
END LOOP;

Using %FOUND
%FOUND is the logical opposite of %NOTFOUND. It evaluates to TRUE if
the last FETCH succeeded because a row was available, or to FALSE if the last
FETCH failed because no more rows were available. The following example
uses %FOUND to take either of two alternative actions.
LOOP
FETCH emp_cursor INTO emp_name,dept_num;
IF emp_cursor%FOUND THEN
INSERT INTO my_table VALUES.....
ELSE EXIT;
END IF;
................
END LOOP;

Using %ROWCOUNT
%ROWCOUNT returns the number of rows FETCHEED from the active set so
far. The following example uses %ROWCOUNT to take action if more than 10
rows have been fetched:
LOOP
FETCH emp_cursor INTO emp_name,dept_num;
IF emp_cursor %ROWCOUNT > 10 THEN
--more than 10 rows has been fetched
EXIT;
END IF;
.................
END IF;

Using %ISOPEN
%ISOPEN evaluates to TRUE if an explicit cursor is open and to FALSE if it is
closed. The following example uses %ISOPEN to select an action:
IF emp_cursor%ISOPEN THEN
FETCH emp_cursor INTO emp_name,dept_num;
ELSE
OPEN emp_cursor;
END IF;

Implicit Cursor Attributes


Using the implicit SQL%cursor ORACLE implicitly opens a context area to
process each SQL statement. If the statement is a query, you can control its
processing by using the OPEN, FETCH and CLOSE statements to manipulate a
cursor. Even when the SQL statement is not a query, there is useful information
stored in implicit ORACLE context areas.
To give you access to this information, PL/SQL lets you refer to the most
recently opened context area not associated with an explicit cursor as the
SQL%cursor. Although you cannot use the OPEN, FETCH and CLOSE
statements to manipulate the SQL%cursor, you can use cursor attributes to
access its context area.
This means that you can get information about the execution of INSERT,
UPDATE, DELETE and single row SELECT statements (remember that multirow SELECTS use explicit cursors or cursor FOR loops).
You can use the four cursor attributes to access the SQL% cursor's context area:
%NOTFOUND, %FOUND, %ROWCOUNT and %ISOPEN.

Using %NOTFOUND
SQL%NOTFOUND evaluates to TRUE if an INSERT, UPDATE or DELETE
affected no rows, or a single row SELECT returned no rows.
In the last case, the NO_DATA_FOUND predefined exception will be raised
(exceptions are explained later in this chapter), unless the select called a SQL
group function.
SQL%NOTFOUND evaluates to FALSE if an INSERT, UPDATE, DELETE
affected one or more rows or a single row SELECT returned one or more rows.
The following example uses SQL%NOTFOUND to take an action if an
employee is not deleted.

DELETE FROM emp WHERE ename='BELL';


IF SQL%NOTFOUND THEN -- there was no employee named BELL
...........................
END IF;

Using %FOUND
SQL%FOUND is the logical opposite of SQL%NOTFOUND. It evaluates to
FALSE if an INSERT, UPDATE or DELETE affected no rows, or a single row
SELECT returned no rows. SQL%NOTFOUND evaluates to TRUE if an
INSERT, UPDATE, DELETE affected one or more rows or a single row
SELECT returned one or more rows.

Using %ROWCOUNT
SQL%ROWCOUNT returns the number of rows affected by an INSERT,
UPDATE or DELETE or returned by a single row SELECT statement. The
following example uses SQL%ROWCOUNT to take an action if more than 10
rows have been updated.
UPDATE emp SET sal=sal*1.1 WHERE dept_no=10;
IF SQL%ROWCOUNT > 10 THEN -- more than 10 rows have been updated.
........................
END IF;

Using %ISOPEN
ORACLE automatically closes an implicit cursor after executing its associated
SQL statement. Because the SQL% cursor is an implicit cursor, SQL%ISOPEN
always evaluates to FALSE.

Example of an Explicit Cursor and Attribute:


Suppose you have a table named DATA_TABLE that stores data (numbers)
collected from laboratory experiments, and you want to analyze the data from
experiment. In the following example, you calculate results and store them in a
table.
DECLARE
num1 data_table.n1%TYPE;
num2 data_table.n2%TYPE;
num3 data_table.n3%TYPE;
result temp.coll%TYPE;
CURSOR c1 IS SELECT n1,n2,n3 FROM data_table WHERE exper_num=1;
BEGIN
OPEN c1;
LOOP
FETCH c1 INTO num1,num2,num3;
EXIT WHEN c1%NOTFOUND;
result:=num2/(num1+num3);
INSERT INTO temp VALUES (result,null,null);
END LOOP;
CLOSE c1;
COMMIT;
END;

Cursor FOR loops


Cursor FOR loops let you implicitly OPEN a cursor, FETCH each row returned
by the query associated with the cursor, and CLOSE the cursor when all rows
have been processed. In most situations that require a cursor, you can use cursor
FOR loops to simplify coding.
Example: The following example uses a cursor FOR loop to do the above task.
DECLARE
result temp.coll%TYPE;
CURSOR c1 IS SELECT n1,n2,n3 FROM data_table WHERE exper_num=1;
data_tab c1%ROWTYPE;
BEGIN
FOR data_tab IN c1
LOOP
result:=data_tab.n2/(data_tab.n1+data_tab.n3);
INSERT INTO temp VALUES (result,null,null);
END LOOP;
COMMIT;
END;

When we use a cursor FOR LOOP, it implicitly declares the variable


data_tab as belonging to the rowtype (c1%ROWTYPE) of the cursor
c1.

The sequence of statements inside the loop is executed once for every
row that satisfies the query associated with the cursor, and for each
iteration a new record will be fetched
from the c1 to data_tab.
Dot notation should be used to make a reference to individual items.

Example: data_tab.n1 where data_tab is the variable and n1 is the name


of the field.

When you leave the loop the cursor is closed automatically. This is
true, even if you use an EXIT or GOTO statements to leave the loop
prematurely, of if an exception is raised inside the loop.

Error Handling in PL/SQL


Whenever a SQL*PLUS statement is executed, if it results into an error
condition, Oracle returns an error number and an error message stating the
Oracle error. PL/SQL has the capabilities of dealing with Oracle errors. It has a
number of conditions that are pre-programmed into it that are recognized as
error conditions. These are called internally defined exceptions.
We can also program PL/SQL to recognize user defined exceptions.
The method used to recognize user-defined exceptions is as follows:

Declare a user-defined exception in the declaration section of the


PL/SQL block.

In your main program block, for the condition that needs special
attention, execute a RAISE statement.

In the exception part of the PL/SQL block, define your exception that
will be invoked automatically when the condition for raise is
satisfied.

The following table shows the list of pre-defined exceptions.


Exception
DUP_VAL_ON_INDEX

LOGIN_DENIED
NO_DATA_FOUND
NOT_LOGGED_ON
PROGRAM_ERROR
TIMEOUT_ON_RESOURCE

TOO_MANY_ROWS
VALUE_ERROR
ZERO_DIVIDE
OTHERS

Raised when
An INSERT or UPDATE command
attempts to violate the UNIQUE constraint
of a particular column.
An invalid username/password was used
to log on to ORACLE.
A SELECT statement returns zero rows.
PL/SQL issues an Oracle call without
being logged onto ORACLE.
PL/SQL has an internal problem.
ORACLE has been waiting to access a
resource beyond the user-defined timeout
limit.
A SELECT statement returns more than
one row.
The data type or data size is invalid.
A variable or constant is divided by zero.
Stands for all the other exceptions not
explicitly named in the exception handler.

Example: In the following example, you calculate a bonus based on salary and
commission for each sales person in the sample company. All sales people
should have a non-zero commission. So, if a sales person has a zero
commission, you raise an exception named zero_comm.
DECLARE
zero_comm EXCEPTION;
salary
NUMBER(7,2);
commission NUMBER(7,2);
emp_code emp.empno%TYPE:=&emp_no;
BEGIN
SELECT sal,comm INTO salary,commission FROM emp
WHERE empno=emp_code;
IF commission = 0 OR commission IS NULL THEN
RAISE zero_comm;
ELSE
INSERT INTO BONUS(ename,amount) VALUES
(emp_code,1.5*(sal+comm));
END IF;
COMMIT;
EXCEPTION
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE(' The Employee does not exist');
WHEN zero_comm THEN
INSERT INTO error VALUES('Bonus not calculated');
END;
In the above example, we are inputing an employee number through the
scan (&) operator. If the employee number is not there in the table, the
program will automatically raise the exception,
NO_DATA_FOUND. The user defined exception zero_comm is raised
explictly.

Stored Procedures, Functions and Database


Triggers
Objectives
In this Chapter, you will learn about Stored Procedures, Functions and Database
Triggers.

Topics

Stored Procedures
How Oracle creates a Procedure?
Advantages of Procedures
Deleting the Procedure
Stored Functions
How Oracle creates a Function?
Advantages of Functions
Creating a Function
Deleting a Function
Database Triggers
Use of Database Triggers
Applying a Database Trigger
Types of Triggers
Before Vs After Triggers
Creating a Trigger
Deleting a Trigger
The Raise_Application Error Procedure

Stored Procedures
Procedures are named PL/SQL blocks that can take parameters, perform an
action and can be invoked. A procedure is generally used to perform an action
and to pass values.
Procedures are made up of:
1. A declarative part,
2. An executable part, and
3. An optional exception-handling part.

Declarative Part
The declarative part may contain declarations of cursors, constants, variables,
exceptions and subprograms. These objects are local to the procedure. The
objects become invalid once you exit from it.

Executable part
The executable part contains a PL/SQL block consisting of statements that
assign values, control execution and manipulate ORACLE data. The action to
be performed is coded here and data that is to be returned to the calling
environment is also returned from here. Variables declared are put to use in this
block.

Exception handling
This part contains code that performs an action to deal with exceptions raised
during the execution of the executable part. This block can be used to handle
Oracle's own exceptions or the exceptions that are declared by the user. One
cannot transfer the flow of execution from the exception handling part to the
executable part or vice versa.

How ORACLE creates a Procedure?


Procedures in ORACLE are called Stored Procedures, which are stored in the
database and are invoked or called by any anonymous block (the PL/SQL block
that appears within an application). When a Procedure is created, ORACLE
automatically performs the following steps:
1. Compiles the procedure.
2. Stores the compiled code.
3. Stores the procedure in the database.

The PL/SQL compiler compiles the code. If an error occurs, then the procedure
is created but it is an invalid procedure. ORACLE, display a message during the
time of creation that the procedure was created with compilation errors. If one
wants to display the errors, one has to use the following SELECT statement:
SQL> SELECT * FROM USER_ERRORS;
ORACLE loads the compiled procedure in the memory area called the System
Global Area (SGA). This allows the code to be executed quickly. The same
procedure residing in the SGA is executed by other users also.
ORACLE performs the following steps to execute a procedure:
1. Verifies user access: ORACLE checks if the user who called the procedure
has the execute privilege on the procedure.
2. Verifies procedure validity: ORACLE checks, whether the procedure is a
valid procedure or not. The user can see the validity of the procedure using the
following SELECT statement.
SQL> SELECT object_name,object_type,status FROM user_objects WHERE
object_type='PROCEDURE';
3. Executes the procedure: If the status is valid then, the procedure is loaded
into the memory, and executed.

Advantages of Procedures
1. Security
Stored procedures help enforce data security. For e.g. you can grant users access
to procedure that can query a table, but not grant them access to the table itself.

2. Performance
It improves database performance in the following ways:
* Amount of information sent over a network is less.
* No compilation step is required to execute the code.
* As procedure is present in the shared pool of SGA retrieval from disk
is not required.

3. Memory allocation
Reduction in memory as stored procedures have shared memory capabilities so
only one copy of procedure needs to be loaded for execution by multiple users.

4. Productivity
Increased development productivity, by writing a single procedure we can avoid
redundant coding and increase productivity.

5. Integrity
Improves integrity, a procedure needs to be tested only once to guarantee that it
returns an accurate result. Hence coding errors can be reduced.

Creating a Procedure
A procedure can be created using the CREATE PROCEDURE command.
Syntax: CREATE [OR REPLACE] PROCEDURE [schema.] {procedure_name}
(argument {IN, OUT, INOUT} datatype,...) {IS, AS}
local variable declarations;
BEGIN
PL/SQL subprogram body;
EXCEPTION
handle the exceptions here;
END;
The keywords and the parameters used are explained below:

REPLACE

Schema

Procedure_name
Argument
IN
OUT
INOUT

Datatype
Subprogram

Recreates the procedure if it already exists. You can use


this option to change the definition of an existing
procedure without dropping. If you redefine a procedure
ORACLE redefines it.
is the schema to contain the procedure
. ORACLE takes the default schema to be the current
schema, if omitted.
is the name of the procedure to be created.
is the name of an argument to the procedure. Parenthesis
can be omitted if no arguments are present.
Specifies that you must specify a value for the argument
when calling the procedure.
Specifies that procedure passes a value for the argument
back to its calling environment after execution.
Specifies that you must specify a value for the argument
when calling the procedure and that the procedure passes
a value for this argument back to its calling environment
after execution. By default it takes IN.
Is the datatype of an argument. It supports any datatype of
PL/SQL.
Is the definition of the procedure consisting of PL/SQL
statements.

Example: To create a procedure that takes employee number and increment in


the salary as the arguments, and increases the salary of that employee by that
amount, if the employee's salary is less than $ 2000, else to decrease the salary
by that amount.
CREATE OR REPLACE PROCEDURE update_sal ( emp_code IN NUMBER,
incr IN NUMBER) IS salary NUMBER(7,2);
BEGIN
SELECT sal INTO salary FROM emp WHERE empno=emp_code;
IF salary < = 2000 THEN
UPDATE emp SET sal = sal + incr WHERE empno=emp_code;
ELSE
UPDATE emp SET sal = sal - incr WHERE empno=emp_code;
END IF;
COMMIT;
END;
To execute this procedure, user EXEC command, at the SQL prompt.
SQL> EXEC update_sal(101,200);
where 101 is the employee number, and 200 is the increment or decrement in
the salary depending upon whether 101's salary is greater that 2000 or not. To
call this procedure within the PL/SQL block, just name of the procedure with
arguments is enough.
Example:
BEGIN
update_sal(101,200);
END;

Deleting the Procedure


A Procedure can be deleted from the database using the DROP PROCEDURE
command:
SQL> DROP PROCEDURE update_sal;
Will remove the above procedure from the database.

Stored Functions
Functions are named PL/SQL blocks that can take parameters, perform an
action and return a value to the host environment. A function can return only
one value.
Functions are made up of:
1. A declarative part,
2. An executable part, and
3. An optional exception-handling part.

Declarative part
The declarative part may contain declarations of cursors, constants, variables,
exceptions and subprograms. These objects are local to the function. The
objects become invalid once you exit from it. Here the datatype of the return
value is also declared.

Executable part
The executable part contains a PL/SQL block consisting of statements that
assign values, control execution and manipulate ORACLE data. The action to
be performed is coded here and data that is to be returned to the calling
environment is also returned from here. Variables declared are put to use in this
block.

Exception handling
This part contains code that performs an action to deal with exceptions raised
during the execution of the executable part. This block can be used to handle
Oracle's own exceptions or the exceptions that are declared by the user. One
cannot transfer the flow of execution from the exception handling part to the
executable part or vice versa. The returned value can also be passed from here.

How ORACLE creates a Function


Functions in ORACLE are called Stored Functions, which are stored in the
database and are invoked or called by any anonymous block (the PL/SQL block
that appears within an application). When a Function is created, ORACLE
automatically performs the following steps:
1.Compiles the function.
2.Stores the compiled code.
3.Stores the function in the database.
The PL/SQL compiler compiles the code. If an error occurs, then the function is
created but it is an invalid function. ORACLE displays a message during the
time of creation that the function was created with compilation errors. If one
wants to display the errors, one has to use the following SELECT statement:
SQL> SELECT * FROM USER_ERRORS;
ORACLE loads the compiled function in the memory area called the System
Global Area (SGA). This allows the code to be executed quickly. The same
function residing in the SGA is executed by the other users also.
ORACLE performs the following steps to execute a function:
1. Verifies user access: ORACLE checks if the user who called the function has
the execute privilege on the function.
2. Verifies function validity: ORACLE checks, whether the function is a valid
function or not. The user can see the validity of the function using the following
SELECT statement.
SQL> SELECT object_name, object_type, status FROM user_objects WHERE
object_type='FUNCTION';
3. Executes the function: If the status is valid then, the function is loaded into
the memory, and executed.

Advantages of Functions
1. Security
Stored functions help enforce data security. For e.g. you can grant users access
to functions that can query a table, but not grant them access to the table itself.

2. Performance
It improves database performance in the following ways:

Amount of information sent over a network is less.


No compilation step is required to execute the code.
As function is present in the shared pool of SGA retrieval from disk
is not required.

3. Memory allocation
Reduction in memory as stored functions have shared memory capabilities so
only one copy of function needs to be loaded for execution by multiple users.

4. Productivity
Increased development productivity, by writing a single function we can avoid
redundant coding and increase productivity.

5. Integrity
Improves integrity, a function needs to be tested only once to guarantee that it
returns an accurate result. Hence coding errors can be reduced.

Creating a Function
A function can be created using the CREATE FUNCTION command.
Syntax: CREATE [OR REPLACE] FUNCTION [schema.] {function_name}
(argument IN datatype,...) RETURN datatype {IS, AS}
local variable declarations;
BEGIN
PL/SQL subprogram body;
RETURN value;
EXCEPTION
handle the exceptions here;
RETURN value;
END;

The keywords and the parameters used are explained below:


REPLACE

recreates the function if it already exists. You can use this


option to change the definition of an existing function
without dropping. If you redefine a function ORACLE
redefines it.

schema

is the schema to contain the function. ORACLE takes the


default schema to be the current schema, if omitted.

function_name

is the name of the function to be created.

argument

is the name of an argument to the function. Parentheses


can be omitted if no arguments are present.

IN

specifies that you must specify a value for the argument


when calling the function.

RETURN datatype

is the datatype of the function's return value.. It supports


any datatype of PL/SQL.

subprogram

is the definition of the function consisting of PL/SQL


statements.

Here is an example of the function, which calculates the total salary of the
department, which is passed as an argument.
CREATE FUNCTION dept_tot_sal ( dept IN NUMBER) RETURN NUMBER IS
tot_sal NUMBER(8,2);
BEGIN
SELECT SUM(sal) INTO tot_sal FROM emp WHERE deptno=dept;
RETURN tot_sal;
EXCEPTION
WHEN NO_DATA_FOUND THEN -- if the department does not exist
RETURN 0;
END;
One can call this function in a PL/SQL block as follows:
..........
BEGIN
total_salary:=dept_tot_sal(20);
IF total_salary > 100000 THEN -- Department 20 's total salary is greater than
100000
........
END IF;
.............
END;

Deleting a Function
One can remove a function from the database, using DROP FUNCTION
command.
SQL> DROP FUNCTION dept_tot_sal;
Will remove the above function from the database.

Database Triggers
Database triggers are procedures that are stored in the database and are
implicitly executed when the contents of the associated table are changed.

Use Of Database Triggers


Some of the uses to which the database triggers can be put to customize
management information in ORACLE are as follows:

A trigger can permit DML statement against a table only if they are
issued, during regular business hours or on predetermined weekdays.

A trigger can also be used to keep an audit trail of a table (i.e. to store
the modified and deleted records of table) along with the operation
performed and the time on which the operation was performed.

It can be used to prevent invalid transactions.

Enforce complex security authorizations.

Database Triggers Vs Procedures


There are very few differences between these two. In procedures it is possible to
pass parameters which is not the case with triggers. A trigger is executed
implicitly by Oracle itself upon modification of an associated table whereas to
execute a procedure, it has to be explicitly called by the user.

Database Triggers Vs Declarative Integrity


Constraints
Triggers as well as declarative integrity constraints can be used to constraint
data input. However, both have significant differences as mentioned below:

A declarative integrity constraint is a statement about a database that


is always true. A constraint applies to existing data in the table and
any statement that manipulates the table. Triggers constrain what
transaction can do., A trigger does not apply to data loaded before the
trigger was created, so it does not guarantee all data in table confirms
to the rules established by an associated trigger.

Also a trigger enforces transitional constraint which can not be


enforced by a declarative integrity constraint.

Applying a Database trigger


A trigger has 3 basic parts:
1. A triggering event or statement
2. A trigger restriction
3. A trigger action

Triggering Event or Statement


It is a SQL statement that causes trigger to be fired. It can be INSERT,
UPDATE or DELETE statement for a specific table. A triggering statement can
also specify multiple DML statements.
Triggering restriction
A trigger restriction specifies a Boolean expression that must be TRUE for the
trigger to fire. It is an option available for triggers that are fired for each row. Its
function is to conditionally control the execution of a trigger. A trigger
restriction is specified using a WHEN clause.
Trigger Action
A trigger action is the procedure (PL/SQL block) that contains the SQL
statements and PL/SQL code to be executed when a triggering statement is
issued and the trigger restriction evaluates to TRUE. It can contain SQL and
PL/SQL statements. Additionally, for row triggers, the statements in a trigger
action have access to column values of the current row being processed.

Types of Triggers
The types of triggers are explained below:

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, a row trigger is
fired once for each row affected by the UPDATE statement. If the triggering
statement affects no rows, the trigger is not executed at all. Row trigger should
be used when the trigger action code depends on the data provided by the
triggering statement or rows that are affected.
E.g. if the trigger is keeping the track of all the affected records.

Statement triggers
A statement trigger is fired once on behalf of the triggering statement,
independent of the number of rows the triggering statement affects (even if no
rows are affected). 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.
E.g. if the trigger makes the security check on the time or the user.

Before Vs After Triggers


When defining a trigger you can specify the trigger timing, i.e. you can specify
when the triggering action is to be executed in relation to the triggering
statement. BEFORE and AFTER apply to both row and the statement triggers.

Before Triggers
Before triggers execute the trigger action before the triggering statement. These
types of triggers are commonly used in the following situation:

Before triggers are used when the trigger action should determine
whether or not the triggering statement should be allowed to
complete. By using a BEFORE trigger, you can eliminate
unnecessary processing of the triggering statement.

BEFORE triggers are used to derive specific column values before


completing a triggering INSERT or UPDATE statement.

After Triggers
After triggers execute the trigger action after the triggering statement is
executed. These types of triggers are commonly used in the following situation:

AFTER triggers are used when you want the triggering statement to
complete before executing the trigger action.

If a BEFORE trigger is already present, an AFTER trigger can


perform different actions on the same triggering statement.

Combinations:
Using the options explained above, four types of triggers can be created:
1. BEFORE statement trigger
Before executing the triggering statement, the trigger action is executed.
2.BEFORE row trigger
Before modifying each row affected by the triggering statement and before
appropriate integrity constraints, the trigger is executed if the trigger restriction
either evaluated to TRUE or was not included.
3.AFTER statement trigger
After executing the triggering statement and applying any deferred integrity
constraints, the trigger action is executed.
4. AFTER row trigger
After modifying each row affected by the triggering statement and possible
applying appropriate integrity constraints, the trigger action is executed for the
current row if the trigger restriction either evaluates to TRUE or was not
included. Unlike BEFORE row Triggers, AFTER row Triggers have row
locked.

Creating a Trigger
The CREATE TRIGGER command is used to create a trigger.
Syntax: CREATE OR REPLACE TRIGGER [schema.] trigger_name
{BEFORE, AFTER} {DELETE, INSERT, UPDATE [OF column,....]} ON
[schema.] table_name [REFERENCING {OLD AS old, NEW AS new}]
[FOR EACH ROW [WHEN condition]]
DECLARE
variable declarations;
constant declarations;
BEGIN
PL/SQL subprogram body;
EXCEPTION
exception PL/SQL block;
END;
The keywords and parameters are explained below:
OR REPLACE

recreates the trigger if it already exists. You can use this


option to change the definition of an existing trigger
without first dropping it.

Schema

is the schema to contain the trigger. If you omit the


schema, ORACLE creates the trigger in your own
schema.

trigger_name

is the name of the trigger to be created.

BEFORE

indicates that ORACLE fires the trigger before executing


the triggering statement.

AFTER

indicates that ORACLE fires the trigger after executing


the triggering statement.

DELETE

indicates that ORACLE fires the trigger whenever a


DELETE statement removes a row from the table.

INSERT

indicates that ORACLE fires the trigger whenever a new


row is added to the table through the INSERT command.

UPDATE

indicates that ORACLE fires the trigger whenever an


UPDATE statement changes a value in one of the
columns specified in the OF clause. If you omit the OF
clause, ORACLE fires the trigger whenever an UPDATE
statement changes a value in any column of the table.

ON

specifies the schema and name of the table, on which the


trigger is to be created. If you omit the schema, ORACLE
assumes the table is in your schema. You cannot create a
trigger on a table in the schema SYS.

REFERENCING

specifies the correlation names. You can use the


correlation names in the PL/SQL block and WHEN
clause of a row trigger to refer specifically to old and new
values of the current row. The default correlation names
are OLD and NEW. If your row trigger is associated with
a table named OLD or NEW, you can use this clause to
specify different correlation names to avoid confusion
between table name and the correlation name.

FOR EACH ROW

designates the trigger to be a row trigger. ORACLE fires


a row trigger once for each row that is affected by the
triggering statement and meets the optional trigger
constraint defined in the when clause. If you omit this
clause, the trigger is a statement trigger.

WHEN

specifies the trigger restriction. The trigger restriction


contains a SQL condition that must be satisfied for
ORACLE to fire the trigger. This condition must contain
correlation names, and cannot contain a query. You can
specify the trigger restriction only for the row triggers.
ORACLE evaluates this condition for each row affected
by the triggering statement.

PL/SQL block

is the PL/SQL block that ORACLE executes to fire the


trigger. The PL/SQL block should not contain the
transaction control SQL statements (COMMIT,
ROLLBACK and SAVEPOINT).

Deleting a Trigger
One can remove a trigger from the database using the DROP TRIGGER
command.
Syntax: DROP TRIGGER trigger_name;
Where trigger_name, is the name of the trigger to be dropped.

The RAISE_APPLICATION_ERROR Procedure


ORACLE provides a procedure named raise_application_error, which allows
programmers to issue user-defined error messages.
Syntax: RAISE_APPLICATION_ERROR(error_number,message);
Where
error_number

: is a negative integer in the range -20000 to -20999

message

: is a character string up to 2048 bytes in length.

An application can call this procedure only from an executing stored


subprogram like stored procedures and functions, database triggers. Typically,
this procedure is used in database triggers.
RAISE_APPLICATION_ERROR ends the subprogram, rolls back any database
changes it made, and returns a user-defined error number and message to the
application.

Example 1:
The following trigger checks whether the qty_on_hand does not become
negative. If so, an error messge is given to the user.
CREATE TRIGGER check_qty_on_hand BEFORE UPDATE OF qty_on_hand
ON product_master FOR EACH ROW
DECLARE
new_qty NUMBER(8);
BEGIN
new_qty:=:new.qty_on_hand;
IF new_qty < 0 THEN
raise_application_error(-20001,'Quantity on hand cannot be less than zero');
END IF;
END;

Example 2
This example creates a BEFORE statement trigger named emp_permit_changes,
Which ensures that modification to the emp table are made only on working
days.
CREATE TRIGGER emp_permit_changes BEFORE DELETE OR INSERT OR
UPDATE ON emp
DECLARE dummy INTEGER;
BEGIN
IF TO_CHAR(SYSDATE,'DY')='SAT' OR TO_CHAR(SYSDATE,'DY')='SUN'
THEN
-- if today is Saturday or Sunday,
RAISE_APPLICATION_ERROR(-20501,'May not change the table during week
end');
END IF;
SELECT COUNT(*) INTO dummy FROM company_holidays WHERE
hol_day=TRUNC(SYSDATE);
IF dummy > 0 THEN -- if today is a holiday,
RAISE_APPLICATION_ERROR(-20512,'May not change the table during the
company holidays');
END IF;
END;

Lab Exercises on Stored Procedures, Functions


and Triggers
Objectives
This session has some Lab Exercises on Stored Procedures, Functions and
Triggers.

Topics

Section I Stored Procedures


Solutions - Section I Stored Procedures
Section II Stored Functions
Solutions - Section II Stored Functions
Section III Database Triggers
Solutions - Section III Database Triggers

SECTION 1: STORED PROCEDURES


1.1 Create a procedure, which gets the name of the author and updates in salary
as arguments and updates the salary of that author by that amount.
1.2 Use this procedure to increase the salary of RANDY by an amount 500.
1.3. Execute this procedure for a non-existing author.
1.4.Create a procedure to search whether an author has written books or not.
(Use an out parameter for the procedure).
1.5. Use the above procedure to increment the salary of authors who have
written book(s).
NOTE: Solutions are given at the end. However it is better that you
attempt the solution on your own and refer to the Solutions only in case of
doubt or to confirm the solution.

SOLUTIONS: SECTION 1
SOLUTION 1.1
CREATE OR REPLACE PROCEDURE update_salary
(name_of_author IN VARCHAR2, sal_inc IN NUMBER) IS
BEGIN
UPDATE author SET salary=salary+sal_inc WHERE
NAME=name_of_author;
IF SQL%NOTFOUND THEN
DBMS_OUTPUT.PUT_LINE('The author '||name_of_author||' does not exist');
END IF;
END;
Procedure created.

SOLUTION 1.2
SQL> EXEC update_salary('RANDY',500);
PL/SQL prodcedure successfully completed.

SOLUTION 1.3
SQL> EXEC update_salary('XYZ',200);
The author XYZ does not exist.

SOLUTION 1.4
CREATE OR REPLACE PROCEDURE search_author_book
(name_of_author IN VARCHAR2, yes_no OUT BOOLEAN) IS
dummy CHAR;
BEGIN
SELECT 'x' INTO dummy FROM AUTHOR WHERE name=name_of_author
AND name IN (SELECT name FROM book);
yes_no:=TRUE;
EXCEPTION
WHEN NO_DATA_FOUND THEN
yes_no:=FALSE;
END;

SOLUTION 1.5
DECLARE
written BOOLEAN;
CURSOR all_authors IS SELECT name,salary FROM author;
author_rec all_authors%ROWTYPE;
BEGIN
FOR author_rec IN all_authors LOOP
/* Call the procedure to check whether author has written books or not */
search_author_book(author_rec.name,written);
IF written = TRUE THEN -- The author has written a book.
UPDATE author SET salary=salary + 200 WHERE name=author_rec.name;
COMMIT;
END IF;
END LOOP;
END;

SECTION 2: STORED FUNCTIONS


2.1. Create a function, which takes the language as the argument and calculates
the average monthly salary paid for the authors on that language.
2.2. Use the above function to decrease the salary of HINDI authors, if the
Average Salary of HINDI authors is more than 2500.
NOTE: Solutions are given at the end. However it is better that you
attempt the solution on your own and refer to the Solutions only in case of
doubt or to confirm the solution.

SOLUTIONS: SECTION 2
SOLUTION 2.1
CREATE OR REPLACE FUNCTION Avg_Lang_Salary
(Language IN VARCHAR2) RETURN NUMBER IS
Sum_Salary Number(10,2);
Null_Total Exception;
BEGIN
SELECT SUM(salary) INTO Sum_Salary FROM author
WHERE lang1=Language OR lang2=Language;
IF Sum_Salary IS NULL THEN
RAISE Null_Total;
END IF;
RETURN Sum_Salary;
EXCEPTION
WHEN Null_Total THEN
RETURN 0;
END;
Function Created.

SOLUTION 2.2
DECLARE
Avg_Sal Number(10,2);
BEGIN
Avg_Sal:=Avg_Lang_Salary('HINDI'); --Call the function to calculate.
IF Avg_Sal > 2500 THEN
UPDATE author SET salary=salary-200 WHERE lang1='HINDI'
OR lang2='HINDI';
COMMIT;
END IF;
END;

SECTION 3: DATABASE TRIGGERS


3.1 Create a database trigger to ensure that an author writes a book only in his / her
known language.
3.2 Create a database trigger to ensure that only the authors of age between 21 and 40
are appointed in the company.
3.3 Create a database trigger to ensure that no one alters the table contents on Sundays.
NOTE: Solutions are given at the end. However it is better that you attempt the
solution on your own and refer to the Solutions only in case of doubt or to confirm
the solution.

SOLUTIONS: SECTION 3
SOLUTION 3.1
CREATE OR REPLACE TRIGGER lang_trigger BEFORE INSERT OR
UPDATE OF wri_in ON book FOR EACH ROW
DECLARE
dummy CHAR;
BEGIN
SELECT 'x' INTO dummy FROM author WHERE (lang1=
NEW.wri_in OR lang2=:NEW.wri_in) AND name=:NEW.name;
EXCEPTION
WHEN NO_DATA_FOUND THEN
RAISE_APPLICATION_ERROR(-20001,'The author is not familiar with this
language.');
END;

SOLUTION 3.2
CREATE OR REPLACE TRIGGER age_trigger BEFORE INSERT OR
UPDATE OF dob ON AUTHOR FOR EACH ROW
DECLARE
age NUMBER;
BEGIN
age:= MONTHS_BETWEEN(SYSDATE,:NEW.dob)/12;
IF age NOT BETWEEN 20 AND 40 THEN
DBMS_OUTPUT.PUT_LINE('Age of the author is '||TO_CHAR(AGE));
RAISE_APPLICATION_ERROR(-20001,'Author is Not in the age group of 20
to 40');
END IF;
END;

SOLUTION 3.3
CREATE OR REPLACE TRIGGER appoint_trigger BEFORE INSERT OR
UPDATE OR DELETE ON AUTHOR
BEGIN
IF TO_CHAR(SYSDATE,'DY')='SUN' THEN
RAISE_APPLICATION_ERROR(-20003,'No changes on Sundays');
END IF;
END;

Game of Cricket Lab Exercises


Objectives
In this session, you will create 5 tables Personal Information of players,
batsman details, bowler details, match-batting details and match-bowling details
with appropriate constraints. Also you will write queries and PL/SQL
validations based on the above tables.

Topics

Section I - Tables
Section I Solutions - Tables
Section II - Queries
Section II Solutions - Queries
Section III PL/SQL Validations
Section III Solutions - PL/SQL Validations

Game of Cricket
SECTION I: TABLES
1. Create a table with the following structure, which holds the personal
information of players.
TABLE 1:STRUCTURE
Name
NAME
TEAM
PLAYER_ID
DOB
FIRST_PLAY_DATE

Null?
NOT
NULL
NOT
NULL
NOT
NULL
NOT
NULL
NOT
NULL

Type
VARCHAR2(20)

Description
Players name.

CHAR(1)

Name of the team

NUMBER(2)

ID of the Player

DATE

Date of Birth of the


Player
Players First Play
Date
Players Batting
Arm
Players Bowling
Arm

DATE

BAT_ARM

CHAR(1)

BOWL_ARM

CHAR(1)

Constraints:

Team and Player id should be primary key.


Team should be A, B, C or D
A player should be in a team only when he is 14 years old.
Bat arm and Bowling arm should be either R or L.

2. Create a table with the following structure, which holds the details of batsmen.
TABLE 2: STRUCTURE
Name
TEAM

Type
CHAR(1)

Description
Name of the Team

NUMBER(2)

Id of the Player

MATCHES

NUMBER(3)

INNINGS

NUMBER(3)

TOTAL_RUNS

NUMBER(5)

TOTAL_BALLS

NUMBER(4)

No of matched
played by the
player
No of matches, the
player has batted
Total Runs scored
by the player.
Total balls faced by
the player.

PLAYER_ID

Null?
NOT
NULL
NOT
NULL

Constraints

Team and Player id should reference personal info.


Number of matched should be less than or equal to the innings.

3. Create a table with the following structure, which holds the details of bowlers.
TABLE 3: STRUCTURE
Name
TEAM
PLAYER_ID
MATCHES

Null?
NOT NULL
NOT NULL

Type
CHAR(1)
NUMBER(2)
NUMBER(3)

Description
Name of team
Id of the Player
No of matches
played by the
player

WICKETS

NUMBER(4)

BALLS

NUMBER(5)

No of wickets taken
by the player
No of balls bowled
by the player

Constraints:

Team and Player id should reference personal info.


Wickets should be less than or equal to the no of balls.

4. Create a table with the following structure, which holds the batting details of
matches.
TABLE 4: STRUCTURE
Name
MATCH_NO
TEAM
PLAYER_ID
RUNS
NO_OF_FOURS
NO_OF_SIXES
BALLS_FACED

STATUS

Null?
NOT
NULL

Type
Description
NUMBER(3) Id of the Match
CHAR(1)
Name of the team
NUMBER(2) ID of the Player
NUMBER(3) Runs scored by a Player in the
match.
NUMBER(2) No of fours scored by a player in
a Match.
NUMBER(2) No of sixes scored by a player in
a Match.
NUMBER(3) No of balls faced by a player in a
Match
CHAR(1)

Status of the player whether


out or not out.

Constraints

Match_no, Team and Player_id is primary key.


Team and Player_id should reference personal_info.
Sum of No of sixes and No of fours scored by a player should be less than or
equal to runs.
Status O for Out and N for Not out.

5. Create a table with the following structure, which holds the bowling details of
matches.

TABLE 5: STRUCTURE
Name
MATCH_NO
TEAM
PLAYER_ID
RUNS_GIVEN

Null?
NOT NULL
NOT NULL
NOT NULL

Type
NUMBER(3)
CHAR(1)
NUMBER(2)
NUMBER(3)

BALLS_BOWLED

NUMBER(3)

WICKETS

Number(2)

Description
Id of the match
Name of the Team
Id of the Player
No of Runs given by the
bowler in the match.
No of balls bowled by the
bowler in a match.
No of wickets taken by the
bowler in a match.

Constraints

Match_no, Team and Player_id is the primary key.


Team and Player_id should reference personal_info.
No of wickets per bowler per match should not exceed 10.
No of balls, bowled by a bowler in a match should not exceed 60.

SOLUTION SECTION I: TABLES


SOLUTION TABLE 1:PERSONAL_INFO
CREATE TABLE PERSONAL_INFO
(TEAM CHAR CONSTRAINT CK_TEAM CHECK(TEAM IN('A','B','C','D')),
PLAYER_ID NUMBER(2),
DOB DATE NOT NULL,
FIRST_PLAY_DATE DATE NOT NULL,
BAT_ARM CHAR DEFAULT 'R' CONSTRAINT CK_BAT CHECK(BAT_ARM IN
('R','L')),
BOWL_ARM CHAR DEFAULT 'R' CONSTRAINT CK_BOWL
CHECK(BOWL_ARM IN ('R','L')),
CONSTRAINT PK_TID PRIMARY KEY(TEAM,PLAYER_ID),
CONSTRAINT CK_FIRST
CHECK(MONTHS_BETWEEN(FIRST_PLAY_DATE,DOB)/12 > 14));

SOLUTION TABLE 2: BATSMAN_DETAILS


CREATE TABLE BATSMAN_DETAILS(
TEAM CHAR ,
PLAYER_ID NUMBER(2),
MATCHES NUMBER(3),
INNINGS NUMBER(3),
TOTAL_RUNS NUMBER(5),
TOTAL_BALLS NUMBER(4),
FOREIGN KEY (TEAM,PLAYER_ID) REFERENCES PERSONAL_INFO,
CONSTRAINT CK_MI CHECK(MATCHES<=INNINGS),

SOLUTION TABLE 3: BOWLER_DETAILS


CREATE TABLE BOWLER_DETAILS(
TEAM CHAR,
PLAYER_ID NUMBER(2),
MATCHES NUMBER(3),2
WICKETS NUMBER(4),
BALLS NUMBER(5),
CONSTRAINT PK_TID PRIMARY KEY(TEAM,PLAYER_ID),
FOREIGN KEY (TEAM,PLAYER_ID) REFERENCES PERSONAL_INFO,
CONSTRAINT CK_WB CHECK(WICKETS<=BALLS));

SOLUTION TABLE 4: MATCH_BAT_DETAILS


CREATE TABLE MATCH_BAT_DETAILS(
MATCH_NO NUMBER(3) NOT NULL,
TEAM CHAR,
PLAYER_ID NUMBER(2),
RUNS NUMBER(3),
NO_OF_FOURS NUMBER(2),
NO_OF_SIXES NUMBER(2),
BALLS_FACED NUMBER(3),
STATUS CHAR DEFAULT 'O' CONSTRAINT CK_ST CHECK(STATUS IN
('O','N')),
FOREIGN KEY (TEAM,PLAYER_ID) REFERENCES PERSONAL_INFO,
CONSTRAINT pKEY_MTP primary key (TEAM,PLAYER_ID,MATCH_NO),
CONSTRAINT CK_FSR
CHECK(6*NO_OF_SIXES+4*NO_OF_FOURS<=RUNS));

SOLUTION TABLE 5: MATCH_BOWL_DETAILS


CREATE TABLE MATCH_BOWL_DETAILS(
MATCH_NO NUMBER(3) NOT NULL,
TEAM CHAR,
PLAYER_ID NUMBER(2),
RUNS_GIVEN NUMBER(3),
BALLS_BOWLED NUMBER(3),
WICKETS NUMBER(2),
CONSTRAINT PK_MT PRIMARY KEY (MATCH_NO,TEAM,PLAYER_ID),
FOREIGN KEY (TEAM,PLAYER_ID) REFERENCES PERSONAL_INFO,
CONSTRAINT CK_WI CHECK(WICKETS<=10),
CONSTRAINT CK_OV CHECK(BALLS_BOWLED<=60));

SECTION II: QUERIES


1.Display all the ALLROUNDERS of the TEAM D.
2. Display the Players name, Team and How many matches he did not bat
though he was included in the team.
3. Display the Player, Team and Total runs for the player who is less than 16
years old but has scored more than 3000 runs.
4. Display all the Players of the Team A with the statistics of Total Runs and
Total Wickets even through the Player has not taken any wickets or scored any
runs.
5. Display the Players of Team A who have a greater batting average than
anybody in Team C.

SOLUTION SECTION II: QUERIES


SOLUTION 1.
SELECT P.NAME FROM BATSMAN_DETAILS B, BOWLER_DETAILS D
PERSONAL_INFO P WHERE B.TEAM = D.TEAM AND B.PLAYER_ID =
D.PLAYER_ID AND B.TEAM = P.TEAM AND B.PLAYER_ID =
P.PLAYER_ID AND P.TEAM = 'D';

SOLUTION 2.
SELECT B.TEAM, P.TEAM, (B.MATCHES - B.INNINGS) "NOT PLAYED"
FROM PERSONAL_INFO P, BATSMAN_DETAILS B WHERE P.TEAM =
B.TEAM AND P.PLAYER_ID = B.PLAYER_ID;

SOLUTION 3.
SELECT P.NAME, P.TEAM, B.TOTAL_RUNS FROM PERSONAL_INFO P,
BATSMAN_DETAILS B WHERE P.TEAM = B.TEAM AND P.PLAYER_ID =
B.PLAYER_ID AND B.TOTAL_RUNS > 3000 AND
MONTHS_BETWEEN (SYSDATE , P.DOB) /12 <16;

SOLUTION 4.
SELECT P.NAME, B.TOTAL_RUNS, D.WICKETS, DECODE
(P.BAT_ARM,'L','LEFT', 'R','RIGHT') BATARM FROM PERSONAL_INFO P,
BATSMAN_DETAILS B, BOWLER_
DETAILS D WHERE P.TEAM = B.TEAM(+) AND P.PLAYER_ID =
B.PLAYER_ID(+) AND P.TEAM = D.TEAM(+) AND P.PLAYER_ID =
D.PLAYER_ID(+) AND P.TEAM='A';

SOLUTION 5.
SELECT P.NAME FROM PERSONAL_INFO P, BATSMAN_DETAILS B
WHERE
P.TEAM = 'A' AND P.TEAM = B.TEAM AND P.PLAYER_ID =
B.PLAYER_ID
AND TOTAL_RUNS/INNINGS > ANY (SELECT TOTAL_RUNS/INNINGS
FROM
BATSMAN_DETAILS WHERE TEAM = 'C';

SECTION III: PL/SQL Validations


Write the following PL/SQL Validations.
1. Register a Player as soon as his Personal Information is recorded.
2. For a particular match, the total number of balls bowled for a team should
not exceed 300.
3. Update the bowler and batsman details as and when he completes a match.
4. Create a separate view for each team to get the full information.

SOLUTIONS - SECTION III: PL/SQL Validations


SOLUTION: 1
CREATE OR REPLACE TRIGGER REGISTER_PLAYER_DETAILS
BEFORE INSERT ON PERSONAL_INFO FOR EACH ROW
BEGIN
/* This registers the player as a batsman with no score,
no innings, no matches, etc.*/
INSERT INTO BATSMAN_DETAILS VALUES
(:NEW.TEAM,:NEW.PLAYER_ID,0,0,0,0,0);
/* This registers the player as a bowler with no score,
no wickets, no matches, etc.*/
INSERT INTO BOWLER_DETAILS VALUES
(:NEW.TEAM,:NEW.PLAYER_ID,0,0,0);
END;

SOLUTION: 2
This problem is solved using packaged variables, and two triggers in order to
avoid the mutating table problem.
CREATE OR REPLACE PACKAGE packballs AS
P_BALLS NUMBER:=0; -- to hold the no.of balls bowled.
P_TEAM CHAR;
-- to hold the team name.
P_MATCH_NO NUMBER; -- to hold the id of the match.
END packballs;

--This triggers assigns the value for the packaged variables whenever an
insertion or updation is done.
CREATE OR REPLACE TRIGGER CHECKBALLS
BEFORE INSERT OR UPDATE OF BALLS_BOWLED ON
MATCH_BOWL_DETAILS
FOR EACH ROW
DECLARE
V_TOT_BALLS MATCH_BOWL_DETAILS.BALLS_BOWLED%TYPE;
BEGIN
PACKBALLS.P_TEAM := :NEW.TEAM; --register the team.
PACKBALLS.P_MATCH_NO := :NEW.MATCH_NO;
--register the match
id.
END;
--This trigger reads the package variables and validates the insertion or
updation.
CREATE OR REPLACE TRIGGER CHECKLIMITOVERS AFTER
INSERT OR UPDATE OF BALLS_BOWLED ON MATCH_BOWL_DETAILS
DECLARE
V_TOT_BOWLED NUMBER;
BEGIN
SELECT SUM(BALLS_BOWLED) INTO V_TOT_BOWLED FROM
MATCH_BOWL_DETAILS WHERE TEAM=PACKBALLS.P_TEAM AND
MATCH_NO =PACKBALLS.P_MATCH_NO;
IF v_tot_bowled>300 THEN /*If more than 50 overs have been bowled for the
match*/
RAISE_APPLICATION_ERROR(-20001,'OVERS EXCEED 50 FOR THIS
MATCH');
END IF;
PACKBALLS.P_TEAM:=NULL; --reinitialize the packaged variables
PACKBALLS.P_MATCH_NO:=NULL; -to check for the next insertion.
END;

SOLUTION: 3
--update the batsman details.
CREATE OR REPLACE TRIGGER UPDATE_BATSMAN_DETAILS BEFORE
INSERT OR UPDATE ON MATCH_BAT_DETAILS FOR EACH ROW
BEGIN
IF INSERTING THEN -if new batsman details are created
--Add the matches,innings,no.of runs etc.
UPDATE BATSMAN_DETAILS SET MATCHES=MATCHES + 1,
INNINGS=INNINGS +1,TOTAL_RUNS=TOTAL_RUNS+:NEW.RUNS,
TOTAL_BALLS=TOTAL_BALLS+:NEW.BALLS_FACED WHERE
TEAM=:NEW.TEAM AND PLAYER_ID=:NEW.PLAYER_ID;
ELSIF UPDATING THEN
UPDATE BATSMAN_DETAILS SET
TOTAL_RUNS=TOTAL_RUNS-:OLD.RUNS +:NEW.RUNS,
TOTAL_BALLS=TOTAL_BALLS-:OLD.BALLS_FACED +
:NEW.BALLS_FACED WHERE
TEAM=:NEW.TEAM AND PLAYER_ID=:NEW.PLAYER_ID;
END IF;
END;
--update the bowler details.
CREATE OR REPLACE TRIGGER UPDATE_BOWLER_DETAILS BEFORE
INSERT OR UPDATE ON MATCH_BOWL_DETAILS FOR EACH ROW
BEGIN
IF INSERTING THEN
UPDATE BOWLER_DETAILS SET MATCHES=MATCHES + 1,
WICKETS=WICKETS + :NEW.WICKETS,
BALLS=BALLS+:NEW.BALLS_BOWLED WHERE
TEAM=:NEW.TEAM AND PLAYER_ID=:NEW.PLAYER_ID;
ELSIF UPDATING THEN
UPDATE BOWLER_DETAILS SET
WICKETS=WICKETS - :OLD.WICKETS + :NEW.WICKETS,
BALLS=BALLS-:OLD.BALLS_BOWLED +:NEW.BALLS_BOWLED WHERE
TEAM=:NEW.TEAM AND PLAYER_ID=:NEW.PLAYER_ID;
END IF;
END;

SOLUTION: 4
--Example for team A.
CREATE OR REPLACE VIEW team_A AS SELECT
p.name,b.matches,b.total_runs,
d.wickets FROM personal_info p,batsman_details b,bowler_details d
WHERE p.team=b.team AND p.player_id=b.player_id AND
p.team=d.team AND p.player_id=d.player_id AND p.team='A';
SELECT * FROM team_A;
Similarly create views for team_B.

New Features in Oracle 8.0


Objectives
In this Chapter, you will learn about the new features in Oracle 8.0 like Abstract
data types, Varray and Nested Tables.

Topics

Creating Abstract Data Types


Using Object Types in Relational Table
Object Table
Creating a Partitioned Table
Introduction to Varray
Nested Tables
Introduction to Object Views

Creating Abstract Data Types


Abstract Data types are data types that consist of one or more subtypes. Rather
than being constrained to the standard ORACLE data types of NUMBER,
DATE and VARCHAR2, abstract data types can more accurately describe your
data. The user can create new abstract data types. The new abstract data types
can be used in tables and other database objects. User defined types make it
possible to carry more of the structure into the schema. When we define the data
type we use the create or replace command.
Syntax
SQL> Create or replace type <type_name> as object(
Column name1 datatype,
Column name2 datatype,
column namen datatype);

Using the above, we can create new abstract data type.


For Example
SQL> Create or replace type address as object(
add1 number(5),
add2 varchar2(10),
add3 varchar2(10),
add4 number(7));

The above command creates an object named address. The object types that are
created can be made public. This type could be used in other database objects
such as tables, procedures etc. It is possible to nest the user defined data types
i.e., a type can be enclosed within another type. The following example
illustrates this.
SQL>Create or replace type emp as object(
eno number(2),
ename varchar2(10),
eadd address);

Using Object Types in Relational Table


Example:
SQL>Create or replace table emp(
ename varchar2(20),
empno number(4),
sal number(11,2),
commission number(6,2),
eadd address);

Insertion of values into table with object types


The values being inserted into the table are preceded by the type name. The
following example explains the concept.
SQL>Insert into emp(ename, eadd) values('SCOTT', address
(241,'Mark Street','London', 600010));

To retrieve a specific value from a column that has user defined


data type:
Example:
SQL>Select a.empno, a.eadd.add1 from emp a;

Using user defined data type in where clause:


Example:
SQL>Select a.empno from emp a where a.eadd.add1=241;

Updating a column, which has a user defined data type:


Example:
SQL>Update emp a set a.eadd=address(241,'Mark Street',
'London', 600010) where a. ename='SCOTT';

Deleting a row from a table, which has user defined data type:
Example:
SQL>Delete from emp e where e.eadd.add1=241;

Object Table
The additional feature in Oracle 8 is that the tables can be partitioned and stored
in different locations as per requirement. A single logical table can be split into
many physically separate pieces based on ranges of key values. Each of the
parts of the table is called a partition. Although, the partitions are held and
managed independently, they can be queried and updated by reference to the
name of the logical table. Oracle 8 provides partition transparency. The
application does not require the knowledge that the table has been partitioned.
There is a difference between a table, which has a single partition, and a table
that has no partitions. A non-partitioned table cannot be partitioned later. Each
partition is stored in a different segment and has different physical attributes.
Table partitions can be stored in different table spaces. We can access and
manipulate data in one partition even if some or all of the other partitions are
unavailable.
Storing the partitions in different table spaces has its advantages:
1. Reduces the possibility of data corruption in multiple partitions.
2. Makes it possible to backup and recover each partition independently.
Partitions can be altered, dropped, rebuilt, merged and truncated. Partitions
cant have any synonyms.

Creating a Partitioned Table


To create a partitioned table, you must specify the range of values to use for the
partitions as part of the Create Table.
For example, you will be storing a large number of records in the myemp table,
then you may wish to separate the myemp rows across multiple tables. To
partition the table records, use the PARTITON BY RANGE clause of the
CREATE TABLE command. The range will determine the values stored in each
partition.
Create table myemp (empno number(5),ename varchar2(20),
deptno number(3))
partition by range(deptno)
(partition dno10 values less than(20),
partition dno20 values less than (30),
partition dno30 values less than(maxvalue));
In the above table creation, partition dno10 will be used to store employees who
are working in department number less than 20. Partition dno20 will be used, to
store employees who are working in department number less than 30.
The maxvalue keyword tells ORACLE to use the partition to store any data that
could not be stored in the earlier partitions. Notice that you only specify the
maximum value for the range. The minimum value for the range is implicitly
determined by ORACLE.

Query on partitioned table


To query from the partition dno10, we can issue the following select statement.
Select * from myemp partition(dno10)

Adding new partition


The range of new partition should be higher than the last partition. The
statement to add one more partition name dno40 on the table myemp is
Alter table myemp add partition dno40 values less than (50);
Whenever the new partition is added, the partition bound must collate larger
than the last partition.

Deleting partition
We

can delete an existing partition by using DROP PARTITION option from


ALTER TABLE command. When the partition is dropped the, the records
available in that partitions are also dropped.
Alter table myemp drop partition dno40;

Indexing partitions
You can partition on index also. The index may be partitioned according to the
same range values that were used to partition the table. In the following
example, the CREATE INDEX command for the MYEMP table is used.
Create index myemp_ind on myemp(deptno)
Local (partition dno10_ind, partition dno20_ind,
Partition dno30_ind);

Notice the LOCAL keyword. In this create index command, no ranges are
specified. Instead, LOCAL keyword tells ORACLE to create a separate index
for each partition of the myemp table.

You can also create a global index. A global index may contain values from
multiple partition.
For example
Create index myemp_gind on myemp (deptno)
Global partition by range(deptno)
(Partition dno10_ind values less than (10),
Partition dno20_ind values less than (20),
Partition dno30_ind values less than (30));

Introduction to VARRAY
A varying array is a set of objects, each with the same data type. The size of the
array is limited when it is created. When you create a varying array in a table,
the array is treated as a column in the main table.
Varying arrays, also known as VARRAYS, allow you to store repeating
attributes in tables.
For example suppose you have a project table, and projects have employees
assigned to them. To store different employees working for projects, we can use
VARRAY.
Thus, you can use varying arrays to store the employee names in the PROJECT
table. If projects are limited to 10 employees or fewer, you can create a varying
array with a limit of ten entries. The data type for the varying arrays will be
whatever data type is appropriate for the employee name values. The varying
array can then be populated, so that for each project, you can select the names
of all employees of that project from PROJECT table itself.

Nested Tables
A nested table is a table with in a table. A nested table is a collection of rows,
represented as a column within the main table. For each record within the main
table, the nested table may contain multiple rows. It is a way of storing one-tomany relationship within one table.
Consider a table that contains information about departments, in which each
department may have many employees. In a strict relational model, this will be
created as two tables namely DEPT and EMP.
Nested tables allow you to store the information about employees with the
DEPT table itself. The EMP table records can be accessed directly via the
DEPT table, without the need to perform a join. The ability to select the data
without traversing joins may make the data easier to access for users.
Example:
STEP 1. Creating abstract data type EMP_TYPE.
SQL> CREATE OR REPLACE TYPE EMP_TYPE AS OBJECT
(
EMPNO NUMBER(4)
ENAME VARCHAR(20)
SAL NUMBER(7,2)
);
STEP 2. Creating a data type EMP_NT for nested table.
SQL> CREATE TYPE_NT AS TABLE OF EMP_TYPE;
STEP 3. Creating a nested table using Nested data type EMP_NT.
SQL> CREATE TABLE DEPT
(
DEPTNO NUMBER(2)
DNAME VARCHAR(20)
EMPDET EMP_NT) NESTED TABLE EMPDET STORE AS EMP_NT_TAB
);
In Step 1, the EMP_TYPE data type contains a record for each employee which
comprises of EMPNO, ENAME, SAL.
In Step 2, the AS TABLE OF clause of this CREATE TYPE command tells
ORACLE that you will be using this type as the basis for a nested table. The
name of the nested data type is EMP_NT.
In Step 3, the DEPT table is created, with column EMPDET of data type
EMP_NT.

When creating a table that includes a nested table, you must specify the name of
the table that will be used to store the nested tables data. That is, the data for
the nested table is not stored in-line with the rest of the tables data. Instead it is
stored apart from the main table.
Thus data in the EMPDET column will be stored in one table, and the deptno,
dname will be stored separately. ORACLE will maintain pointers between the
tables. In this example, the out-of-line data for the nested table is stored in a
table named EMP_NT_TAB. Although the name of the table such as
EMP_NT_TAB is specified during creation, you cannot perform normal table
related functions on it. Even you cannot DESCRIBE the table.

Inserting Records into Nested Table


You can insert records into a nested table by using EMP_NT data type. The
EMP_NT type in turn uses the EMP_TYPE data type to insert records. As
shown in the following example, inserting a record into the DEPT table requires
us to use both the EMP_NT and EMP_TYPE data types.
Example: Insertion of records into nested table
SQL>INSERT INTO DEPT VALUES(10, ACCTS, EMP_NT(
EMP_TYPE (1000, ROBERT, 1800),
EMP_TYPE (1001, MIKE, 1500),
EMP_TYPE (1002, JOHN,1700)));
SQL>INSERT INTO DEPT VALUES(20, BILLS, EMP_NT(
EMP_TYPE (2000, BOB, 1800),
EMP_TYPE (2001, LUCY, 1500),
EMP_TYPE (2002, SCOTT ,1700)));
SQL>INSERT INTO DEPT VALUES(30, BILLS, EMP_NT(
EMP_TYPE (3000, CNANDE, 1800),
EMP_TYPE (3001, CHAN, 1500),
EMP_TYPE (3001, CRUSET, 1700)));

Querying Nested Table


Nested tables support a great variety of queries. However, you need to consider
the nature of the table during the queries. A nested table is a column within a
table. For querying nested tables, Oracle provides a new keyword THE
To see how the THE keyword is used, first consider the nested table by itself. If
it were a normal column of a relational table, youd be able to query it via a
normal SELECT statement.
SQL> SELECT SAL FROM EMP_NT
WHERE ENAME = ROBERT;
/*THIS QUERY WONT WORK*/

But, EMP_NT is not a normal table. It is a data type. In order to SELECT


columns from the nested table, you first have to flatten the table so that it can
be queried. Thats where the THE function is used.
Example: Query from nested table
SQL> SELECT NT.EMPNO, NT.ENAME, NT.SAL FROM
THE (SELECT EMPDET FROM DEPT WHERE DEPTNO = 10) NT;
The above query will display all employees working in department number10.
SQL>SELECT NT.SAL FROM
THE (SELECT EMPDET FROM DEPT WHERE DEPTNO = 10) NT
WHERE NT.ENAME=ROBERT;
The above query will display the employee whose name is ROBERT and who
works in department number 10.
Example: Deleting a record from nested table
SQL>DELETE FROM THE (SELECT EMPDT FROM DEPT
WHERE DEPTNO = 10) NT
WHRE NT.ENAME = ROBERT;

Further use of THE Function


You can use THE function whenever you need to perform INSERTs or
UPDATEs directly against the nested table. For example, it is likely that a
DEPT will have more employees as time goes by, so you will need the DEPT
table. You will have to insert records into the nested table without adding new
records into the DEPT table, and you will need to relate the new employees into
DEPT table.
Example:
SQL>INSERT INTO THE (SELECT EMPDET FROM DEPT WHERE
DEPTNO=20) VALUES (2004, GEORGE, 2500);

Keywords CAST and MULTISET


ORACLE 8.0 has two keywords CAST and MULTISET. The cast keyword
allows you to cast the result of a query as nested table. The MULTISET
keyword allows the cast query to contain multiple records. You can CAST and
MULTISET together. To effectively use nested tables in your SQL, you should
be familiar with the use of THE, CAST and MULTISET keywords.

Introduction to Object Views


Just as a view is a virtual table, an object view is also a virtual object table.
Oracle provides object views as an extension of the basic relational view
mechanism. By using object views, you can create virtual object tables from
data of either built-in or user defined types stored in the columns of relational or
objects in the database.
Object views allow use of relational data in object-oriented applications. They
let users
Try object oriented programming techniques without converting existing
tables.
Convert data gradually and transparently from relational tables to object
relational tables.
Use legacy RDBMS data with existing object oriented applications.

Advantages of Object Views

Leads to better performance.


Object views provide a gradual migration path for legacy data.
Object views provide for co-existence of relational and object oriented
applications.

Defining Object Views


The procedure for defining an object view is simple. For example, the following
SQL statement defines an object view.
SQL>CREATE TABLE EMP_TABLE
(
EMPNUM NUMBER(5),
ENAME VARCHAR(30),
SALARY NUMBER(9,3),
JOB VARCHSR(20));
SQL>CREARE TYPE EMPLOYE_T
(
EMPNO NUMBER(5),
ENAME VARCHAR(30),
SALARY NUMBER(9,3);
JOB VARCHAR(20));
SQL>CREATE VIEW EMP-VIEW1 OF EMPLOYEE_T
WITH OBJECT OID(EMPNO) AS
SELECT E.EMPNUM, E.ENAME E.SALARY, E.JOB
FROM EMP_TABLE

Using Object Views


Data in the rows of an object view may come from more than one table, but the
object still traverses the network in one operation. When the instance is in the
client side object cache, it appears to the programmer as a C or C++ structure or
a PL/SQL object variable. You can manipulate it like any other native structure.

Updating Object Views


You can update, insert, and delete the data in an object using the same SQL
DML statements you use for object tables. Oracle updates the base tables of the
object view if there is no ambiguity.
A view is not updateable if its view query contains joins, set operators, group
functions, GROUPBY, or DISTINCT. If a view query contains pseudo-columns
or expressions, the corresponding view columns are not updateable. Object
views often involve joins.
To overcome these obstacles, Oracle 8.0 provides INSTEAD OF triggers. They
are called INSTEAD OF triggers because Oracle executes the trigger body
instead of the actual DML statement.
INSTEAD OF trigger provide a transparent way to update object views or
relational views. You write the same SQL DML (INSERT, DELETE and
UPDATE) statements as for an object table. Oracle invokes the appropriate
trigger instead of the SQL statement, and the actions specified in the trigger
body take place.

NOTE: Object views can be created with WITH READ ONLY option and it
supports WITH CHECK OPTION also.

Anda mungkin juga menyukai