SlideShare a Scribd company logo
Oracle 10g SQL



      This book belongs to




      Name       : ______________________________________



      Batch      : ______________________________________




                     SQL Star International Ltd.
                                SQL Star House,
                              No. 8-2-293/174/A 25,
                            Road No. 14, Banjara Hills,
                              Hyderabad - 500 034,
                             Andhra Pradesh, INDIA




© SQL Star International Ltd.
Copyright © 2008
                                      Second Edition



          SQL STAR INTERNATIONAL LIMITED

           SQL Star House,8-2-293/174/A25, Road No.14,
                Banjara Hills, Hyderabad - 500 034.
                Tel. No. 91- 40-23101600(30 lines)
                          Fax No. 23101663
                    Toll Free No: 1800 425 2944


                           Email:         info@sqlstar.com




No part of this publication may be reproduced (incl. photocopying) in any way, without prior
agreement and written permission of SQL Star International Ltd., Hyderabad. SQL Star
International Ltd., Hyderabad assumes no responsibility for its use, nor for any infringements
of patents or other rights of third parties which could result.




© SQL Star International Ltd.                                                                i
Table of Contents

                                Oracle 10g SQL

 CHAPTER                        CHAPTER TITLE                PAGE
   No.                                                        NO
      1.      Database concepts                                 1-39

      2.      Introduction to Oracle 10g                       40-49

      3.      Data Retrieval                                   50-78

      4.      Enhancing Data Retrieval                         79-95

      5.      Generating formatted reports using isql*plus    96-128

      6.      SQL single Row Functions                       129-154

      7.      Working with Grouped Data                      155-163

      8.      Joins                                          164-186

      9.      Understanding Sub queries                      187-201

     10.      Advanced Sub queries                           202-221

     11.      Data Manipulation                              222-248

     12.      Managing Tables                                249-293

     13.      Managing Constraints                           294-318

     14.      Views                                          319-342

     15.      Other Database Objects                         343-371

     16.      Data Dictionary Views                          372-380

     17.      Security Implementation                        381-393

     18.      Manipulating Large Data Sets                   394-413

     19.      Regular Expressions                            414-422




© SQL Star International Ltd.                                          ii
Chapter 1




                                Database Concepts
                                     Typical Database Architecture
                                                            DBMS
                                                   Types of DBMS
                                                     Normalization
                                   Entity Relationship (E-R) Model
                                                   Features of SQL




© SQL Star International Ltd.                                   1
Objectives
At the end of this chapter, you will be able to:

Understand the basic concepts of a database

Identify the disadvantages with Flat File systems

Identify the advantages of a DBMS

Understand the types of DBMS

Understand the E-R Model

Understand the features of SQL

Describe the Codd‘s Rules




© SQL Star International Ltd.                            2
Database Management
The approach of the new millennium has brought with it several challenges, thereby
making it mandatory for companies and organizations to maintain high level of
efficiency in their computing systems, so as to stand the test of time. Databases and
database systems are the essential backbone of any organization.



Database
When one hears the word Database, one thinks of a collection or a store of mutually
related data. The implicit properties of a database are as follows:

      A database represents some aspects of the real world and any changes to the
        real world should get reflected in the database. For example, a manufacturing
        concern keeps details of the products it manufactures and also of the
        suppliers it deals with. Any change in the pricing of the product or a change in
        the suppliers who supply raw materials must be immediately reflected in the
        database.

      A database is a logical collection of relevant data, reflecting some inherent
        meaning. Any random grouping of data cannot be referred to as a database.
        A manufacturing concern requires data about its customers, products, as well
        as its suppliers. Details regarding each of them form a logical group of data.

      A database is populated with data for a purpose. It has an audience that is
        interested in its contents. For instance, in the above example, the
        manufacturing concern needs the customer details to identify its regular
        customers and also their credit worthiness. Similarly product detail helps in
        determining the stock depletion level (i.e. when to place fresh order for raw
        materials).

Now a day, the term „database‟ is mostly used in connection with computerized
databases. Therefore, today, a study of database systems involves also a study of the
associated technology employed to store, access and manipulate the computerized
databases.

Traditionally, data accessed through computers has been stored on different storage
media in the form of individual files. Files proved to be quite satisfactory as long as
computerization was limited to a few application areas and the use of computers
restricted to a privileged few. However, as actual users grew in number, especially
with the advent of online time-sharing systems, the file systems gave rise to many
serious problems. The discipline of database systems evolved in response to these
problems. Let us first consider what these problems are so as to understand the
different features of database systems more clearly.



File Systems and the Associated Problems
Most data processing systems in existence today, especially in India, use files for
storing, accessing and manipulating data. Files are stored typically on magnetic
tapes and disks.


© SQL Star International Ltd.                                                         3
Most of the problems with files arise out of the fact that files are specific to an
application, e.g., a set of files may be designed for the sales analysis system of a
company.

Programs of the same application system can use these files. However, if some
other new application needs source data from this system, there may be difficulties.
Therefore, in many cases, new files, with considerable data in common with the
existing files, may have to be designed for the new applications.

Therefore, as applications proliferate, the total number of computerized files grows
considerably. Also, as the number of actual users of the computer grows, the
number of applications increases, in turn resulting in an increase in the number of
files.

A large number of files give rise to the following problems:


      Files involve a high level of redundancy in data. As we have mentioned above,
       proliferation of files results in the same data item being stored at many
       different places.

      Redundancy in data often results in inconsistency of data. The same data item
       being used by different applications may exist in different versions. What is
       worse, it may exist in different stages of update at different places and thus
       may have different values. This may ultimately result in inconsistencies
       amongst reports generated by the two application systems.

      Individual files are not amendable to rapid changes, especially with respect to
       the way the data items are structured within the file. If an application wants
       data from an existing file but structured differently, it cannot be provided
       quickly and easily. For this purpose, either conversion programs have to be
       written or new files have to be created.

      Because of the inflexibility of files, many ad hoc queries cannot be answered.

      Yet another consequence of the inflexibility of files is that it is usually
       expensive to make changes to a file system. It is also a very slow process. It
       may even involve modification of application programs.

      What is worse, modification in one program may require modifications in
       other programs, which interface with this program. This process may set off a
       chain reaction of modifications.

The above problems give rise to further difficulties detailed below:


      The Management Information Systems (MIS) finds it difficult to control data,
       especially when the actual users develop applications on their own.

      Major changes required in the system while modifying files increase the
       maintenance load on Data Processing (DP) professionals substantially, thus
       making them unavailable for development of new systems.

      High-level data redundancy entails repetitive data entry and redundant
       storage with the accompanying costs.
© SQL Star International Ltd.                                                           4
As has been already stated, Database Systems provide an effective solution to the
above problems. Let us see how.


Data Independence
You have just seen, files give rise to several problems because they are application
specific. Consequently, the applications become data-dependent, that is, they
depend upon the organization and access method for the data on the secondary
storage. This happens because, with conventional application development tools such
as COBOL, the application logic incorporates the knowledge of data organization and
access methods. Therefore, most changes in data organization or access methods
affect the application logic substantially. If problems arising due to this fact are to be
avoided, the data organization (and the access method) and the application logic
have to be made independent of each other. Database Systems do precisely this.

The first step towards this goal is to distinguish between data as is actually stored
(called as the physical representation of data) and data as is presented to an
individual user (called as the logical representation of data).

The Physical Representation of Data
The smallest named unit of data physically stored in the database is known as a
―stored field‖, and a named collection of associated stored fields is known as a
―stored or physical record‖. The named collection of all occurrences of one type of
physical record is known as a ―stored or a physical file‖. This concept will be clearer
after we discuss the logical representation of data.

The Logical Representation of Data
A logical field, record or file is, the field, record or file as it appears to the users, that
is, as it is defined in the user‘s application programs. In all traditional systems, the
logical and physical data are practically the same, which is the root cause of all the
major problems with traditional files. This is not the case with database systems.

Similarly, the structure of stored and logical records can be different. A logical
record type may be obtained by selectively combining fields from different stored
records.
The logical and physical views of a file could also be different in terms of, say, the
key fields for sequencing the records in the file.

With such a separation of the logical and physical data, the database can be modified
and developed without affecting existing applications. The database architecture
achieves this separation.


A Typical Database System
Typical database architecture divides the database into three levels of abstraction;
the internal, conceptual and external levels.

At the internal level is the physical database, while at the external level; one has the
different logical views corresponding to an individual application. The conceptual
level is an intermediate level, which is a single abstract representation of the entire
database.

© SQL Star International Ltd.                                                               5
Data Base Management System (DBMS) is software, which interacts with all the
three levels enabling the users to deal with the data in terms of its logical view
rather than the actual physical database.

A diagrammatic representation of the typical database architecture is shown below:




Let us now consider the different individual entities in the architecture in further
detail. Let us start with the actual or physical database and see how the architecture
brings about a transformation in the data representation to get the data to the user
in the form he wants.

The Internal Database
The internal (or physical) database is stored on secondary storage devices, mainly
the magnetic disk. It itself can be conceptually viewed at different levels of
abstraction. At its lowest level, it is stored in the form of bits with the associated
physical addresses on the secondary storage device.
At its highest level, it can be viewed in the form of files and simple data structures. It
is this level that we shall study when we discuss the physical organization for
databases in later chapters.



© SQL Star International Ltd.                                                           6
The physical database is described by means of a physical scheme or an internal
scheme. It essentially describes the various types of stored records, the different
indexes that are employed for accessing these and the representations for different
stored fields. It is also called as the ―storage structure definition‖.

The Conceptual Database
The conceptual model, also called as the data model, represents information content
of the database in its entirety, but is abstract with respect to the physical database.
Broadly speaking, the conceptual model provides a view of the data as it really is.
This model consists of multiple occurrences of multiple types of a conceptual record.
A conceptual record represents relevant information content only. In this sense, it is
much closer to the external record than a stored record is.

However, it is not the same as the external record.

It contains all the information to build relevant external records. A conceptual stock
record may consist of the quantity of material and the buying rate but not its value;
still the user‘s external record may consist of the value of the stock. A conceptual
model may consist of occurrences of such stock records, a collection of supplier
record occurrences and a collection of assembly records.

Obviously, the conceptual model is derived from the physical model. For this, the
database needs a conceptual/physical mapping, which specifies how conceptual
records and fields map into their counterparts in the physical database. The
conceptual database is described by means of a conceptual scheme. Needless to
say, the conceptual scheme is independent of the physical characteristics of data,
such as storage structures, physical sequences, stored field representations etc.
Ideally the conceptual scheme should include many features in addition to just the
definitions of conceptual records. These may include relevant authorization checks
and validation procedures, the uses of data, the source and destination of data etc.

The conceptual database is a real-world view of data from the organization point of
view. As the real world changes, changes have to be made to the conceptual
database and scheme as well. In such a case, it is usually possible to limit the
corresponding changes to only those external schemes, which use the conceptual
elements that are changed.

The External Database
The external model (or view) is application-specific. Therefore, the user views the
database through an external model, and there are as many external views as there
are applications. External views are the proper interface between the user and the
database as an individual user can hardly be expected to be interested in the entire
database.

Generally, an external model consists of multiple occurrences of multiple types of
external record. An example of an external record is the record of a file as defined in
the data division of COBOL program.

Each external model is defined by means of an external scheme, which describes
each external record type in the external model.

The external model is derived from the conceptual model. For this purpose, the
correspondence between the particular external models has to be defined. An

© SQL Star International Ltd.                                                        7
external/conceptual mapping similar to the conceptual/physical mapping does this.
However, a separate mapping has to be defined for each external view.

An explicit definition of the mapping should be documented, preferably in the
corresponding external scheme.

The user interacts with the database through a high-level language such as COBOL,
PL/I or some special purpose language. This language is known as the host
language. It includes a data sub-language (DSL). The user carries out the retrieval
and storage operations on the database through the DSL.

In fact, the Database Task Group (DBTG) report published in April 1971, contains
proposals for three distinct languages, two of which relate very closely to the concept
of a DSL. These are sub scheme Data Description Language (DDL) and Data
Manipulation Language (DML). The sub scheme DDL is used for defining the external
views while the DML is used for carrying out operations on the database.

In addition to the languages, the user is also supposed to be provided with a
workspace. This workspace is an area meant for receiving or transmitting all data
transferred between the user and the database. This is simply the input-output area
for a program.

Let us now consider what a database management system is, which interacts with
the three levels and the mappings.


What is a Database Management System?
The DBMS is the software, which handles all accesses to the database. Conceptually,
if a user requests a certain data item, the DBMS intercepts and interprets the
request, retrieves the relevant stored occurrences from the physical database,
constructs the required conceptual record occurrences using the physical/conceptual
mapping, then derives the required external record occurrence from the conceptual
records constructed using the relevant conceptual/external mapping.

Advantages of DBMS

You have seen that data independence and the consequential benefits are both an
essential feature and a major advantage of database systems. Yet another essential
feature is the centralization of related data. This phenomenon results in further
advantages of database systems. These are:

      The stored data can be shared relatively easily

      New applications may be developed using the existing database

      Standards for representation of data can be laid down and enforced among
       different installations. This can significantly reduce the maintenance activity
       and enhance data compatibility among installations.

      With a centralized control of data, the database system may be designed for
       an overall optimal performance from the viewpoint of the entire organization.




© SQL Star International Ltd.                                                        8
   Ensuring data security becomes much easier as access to the database can be
        controlled through establishment of proper channels and authorization
        checks.

However, to realize the above benefits, proper organizational infrastructure is
needed. The most popular way to support the Database environment is to establish
the office of the Database Administrator (DBA). In fact, the DBA may be a single
person or a team. He is responsible for the centralized control of the database.


The Database Administrator
The database administrator is responsible for the overall planning of the company‘s
data resources, for the design of data, and for the day-to-day operational aspects of
data management.

The overall planning of corporate data is the strategic aspect of the database
administration function and involves company-wide planning of existing data and
assessment of organization-wise data standards.

Some of the design aspects of database administration work are:

      Deciding on the storage structures and access methods

      Selecting database software and hardware

      Designing restart and recovery procedures to take care of system outages or
        crashes

      Designing means of reconstructing data in the event of abnormal loss of the
        same

      Designing scheme

      Designing the means of reorganizing or tuning databases periodically

      Designing database searching strategies

      Designing authorization checks and validation procedures

      Specifying techniques for monitoring database performance

The operations management of database administration deals with data problems
arising on a day-to-day basis. Specifically, the responsibilities include:

      Investigation of errors found in the data

      Supervision of restart and recovery procedures in the event of a failure

      Supervision of reorganization of databases

      Initiation and control of all periodic dumps of data.




© SQL Star International Ltd.                                                      9
In addition, this aspect of database administration includes maintenance of data
security, which involves maintaining security authorization tables, conducting
periodic security audits, investigating all known security breaches.

To carry out all these functions, it is crucial that the DBA has all the accurate
information about the company‘s data readily on hand. For this purpose he maintains
a data dictionary. The data dictionary contains definitions of all data items and
structures, the various schemes, the relevant authorization and validation checks
and the different mapping definitions. It should also have information about the
source and destination of a data item and the flow of a data item as it is used by a
system. This type of information is a great help to the DBA in maintaining centralized
control of data.




Types of DBMS
The different types of DBMS available are:

      Hierarchical database management system

      Network database management system

      Relational database management system

      Object Relational database management system

Hierarchical DBMS
Hierarchical DBMS (HDBMS) is one of the oldest methods used for organizing and
storing data. In a hierarchical database, data is organized in a pyramid fashion, just
like the branches of a tree extending downwards.

In a hierarchical database you need to understand the concepts of record type and
parent-child relationship. Let us take an example.

In the order processing of any organization, orders are placed for different products.
Orders comprise the following information, which are also called field values:

   •    Order number

   •    Order date


© SQL Star International Ltd.                                                      10
•   Customer number

   •   Product number

Similarly, products comprise a collection of:

   •   Product number

   •   Product type

   •   Product name

   •   Quantity

   •   Price

The collections of these field values are called records and groupings of records of
the same type are called record types. Related records are grouped together so that
you can have higher-level records and lower-level records, similar to how the parents
in a family tree sit above the subordinated children.

In the example, Orders and Products are the two record types and the relationship
between them is the parent-child relationship.




                      Hierarchical Database Management System

In the diagram, the parent record (Orders) at the top of the pyramid is called the
root record. The parent record has three child records linked to it. The root of the
hierarchical model cannot act as the child record type. Except the root, every record
type acts as a child record type in exactly one parent-child relationship.
The child records can have only one parent record. In contrast, a parent record may
have more than one child record linked to it. Each child record can also be a parent
with child records underneath it.

Hierarchical DBMS works by moving from the top of the pyramid to its bottom. A
record search is conducted by working down through the pyramid from parent to
child until the suitable child record is found.

The pyramid like structure and the defining of relationship between records in
advance makes it easy to access and update hierarchical databases.



© SQL Star International Ltd.                                                     11
However, there are few limitations with HDBMS. The relationship between child
records is not permitted, even if they make a logical sense. Moreover, the
hierarchical design is so rigid that adding a new record requires the redefinition of
the entire database.

Network DBMS
Network DBMS (NDBMS) is an extension of HDBMS. Instead of having a pyramid like
structure, a NDBMS looks more like a spider web or interconnected network of
records. In NDBMS, child records are called members and parent records are called
owners.

In the network data model too, data is stored in records and descriptions of the
structure of a group of records of the same type are stored in record types. Record
types are linked or related using the set types. Set types consist of:

          •   A set type name

          •   An owner record type

          •   A member record type

Consider an example of orders and it‘s products. The two record types are Order
and Product, the former being the owner record type and the latter being the
member record type. They are linked using the set type ProdOrder, which
represents the relationship between orders and products in them. The relationship is
of 1:N meaning that there will be many set occurrences (or instances) where one
record from the owner record type Order relates to a set of records from the
member record type Product. That is, an order can have one or more products in it.
Therefore, set occurrences are composed of:

          •   One record from the owner record type

          •   A number of records (zero or more) from the member record type




                          Network Database Management System




© SQL Star International Ltd.                                                     12
In the figure there are three set occurrences of ProdOrder set type, which are
Product1, Product2, Product3.

A record of the member record type cannot exist in more than one set occurrence,
that is, two customers cannot buy the same product.

Similar to HDBMS, NDBMS structure and relationship must be defined in advance.
The number of connections that can be made between records is also limited.

Relational Database
The databases mentioned so far including the file system databases were not very
efficient. In the file system, users cannot simultaneously access data from the same
file, managing the files is very tedious when data stored is complex and accessing
data from files is also very tedious. HDBMS and NDBMS does not allow many-to-
many relationships, has complex path to navigate and retrieve data, and the
relationship between data is in the form of pointers.

The objective of developing the relational model was to overcome the shortcomings
of those systems that existed at the end of the 1960s, and to make DBMS products
more appealing to all kinds of users. Dr. E. F. Codd first introduced the relational
model when he proposed the relational model principles in a paper called ―A
Relational Model of Data for Large Shared Data Banks‖ in June 1970.

A relational database stores data using relations where each relation resembles a
table of values. Each row in a table contains collection of data values. For example, a
university stores information about all it‘s students using tables referred to as a
Student table and a Course table.

Student table contains details about students, such as, their student number, name
and the course code. As different data is stored in the two tables, we may need to
combine them to answer particular questions such as details about students pursuing
course ‗Electronics‘. An RDBMS enables to relate data in one table to the data in
another. It does so by identifying the relationships, which are represented by
primary key and foreign key. A primary key is assigned to that column, which will
enable you to identify each row of data in a table uniquely. For example, in the
Course table the column containing the course code is the primary key as it helps to
identify each course uniquely. A foreign key is assigned to a column of a table, which
refers to the primary key column in another table. For example, in the Student table
the column containing the course code refers to CourseCode column of the Course
table.




© SQL Star International Ltd.                                                       13
Object Relational Database
Hierarchical, network and relational database models have been quite successful in
storing data for traditional business applications. But, object oriented databases
evolved to handle more complex applications such as databases for scientific
experiments, geographic information system, engineering design and manufacturing.
An object oriented database stores data, their relationships and the way they
interact with other data. As compared to the relational database approach, which
deals with data at the lowest level, that is, columns and rows, the object oriented
approach deals with data at a higher level, that is, with the objects surrounding the
data.


RDBMS
Dr. E.F.Codd outlined the principles of the relational model, which formed the basis
for the evolution of the Relational Database Management System.
A Relational Database Management System is defined as a collection of tables
related to each other through common values.



Evolution of RDBMS
Before the acceptance of Codd‘s Relational Model, database management systems
was just an ad hoc collection of data designed to solve a particular type of problem,
later extended to solve more basic purposes. This led to complex systems, which
were difficult to understand, install, maintain and use. These database systems were
plagued with the following problems:

      They required large budgets and staffs of people with special skills that were
        in short supply.

      Database administrators‘ staff and application developers required prior
        preparation to access these database systems.

      End-user access to the data was rarely provided.

© SQL Star International Ltd.                                                      14
   These database systems did not support the implementation of business logic
        as a DBMS responsibility.

Hence, the objective of developing a relational model was to address each and every
one of the shortcomings that plagued those systems that existed at the end of the
1960s decade, and make DBMS products more widely appealing to all kinds of users.

The existing relational database management systems offer powerful, yet simple
solutions for a wide variety of commercial and scientific application problems. Almost
every industry uses relational systems to store, update and retrieve data for
operational, transaction, as well as decision support systems.


Basic Relational Database Terminology
In a relational database, the entities of the ERD are represented as tables and their
attributes as the columns of their respective tables in a database schema. The
components of a database schema include:

       Tables: Tables are the basic storage structures of a database where data
        about something in the real world is stored. It is also called a relation or an
        entity.

       Rows: Rows represent collection of data required for a particular entity. In
        order to identify each row as unique there should be a unique identifier called
        the primary key, which allows no duplicate rows. For example in a library
        every member is unique and hence is given a membership number, which
        uniquely identifies each member. A row is also called a record or a tuple.

       Column: Columns represent characteristics or attributes of an entity. Each
        attribute maps onto a column of a table. Hence, a column is also known as an
        attribute.

       Relationship: Relationships represent a logical link between two tables. A
        relationship is depicted by a foreign key column.

Some optional properties of relational tables include the following:

       Data items (fields) must have a single value.

       Data values in columns are of the same kind. This property states that all
        values in a given column must come from the same domain.


Let us understand the concept of a domain. Suppose, you have a CourseName
column in the Course table, which is defined to be a character string of length 15.
The possible values this column could have are:

       Oracle10g

       Java

       E-commerce

       C++
© SQL Star International Ltd.                                                       15
    Visual Basic



Let us name this list as ‗course-names’ and define a rule that the contents of
CourseName should not only be characters of length less than 15, but must also
contain values that are part of ‗course-names’. Here, ‗course-names’ becomes the
domain and CourseName is in the domain of ‗course-names’.

Each row is unique

       The sequence of columns (left to right) is insignificant. The benefit of this
        property is that columns can be retrieved in any order.

      The sequence of rows (top to bottom) is insignificant. The benefit of this
        property is that rows can be retrieved in any order, that is, the third, fourth
        or fifth row of member details could be retrieved.

       Each column must have a unique name. As mentioned above, the sequencing
        of columns being insignificant, columns must be referred by name and not by
        their position.


Normalization
One of the methods of designing a database is normalization of steps.
What do you mean by normalization?
Normalization can be defined as the technique implemented to remove redundancy
from an existing set of tables.

Normalization helps:

       Reduce redundancy

       Increase integrity

       Stabilize design

       Identify any missing data

A relational table is normalized if it satisfies a certain set of constraints, which are
that they should be free of data redundancy and that they can be modified
consistently and correctly. Therefore, normalization is the process of removing
redundant data by splitting a table into smaller tables.
The technique of normalization includes some rules, which when applied, changes
un-normalized data to a structured and normalized state. The process of normalizing
is implemented in levels called normal forms. There are three such stages, they are:

       First normal form

       Second normal form

       Third normal form




© SQL Star International Ltd.                                                        16
First Normal Form (1NF)
The first normal form can be defined as the level where the tables represent a set of
two-dimensional structures and contain no repeating groups.
You need to implement the following set of steps to convert your un-normalized data
to its first normal form.

      Identify the primary key
      Remove all repeating columns
      Create a new table to contain the repeating columns
      Add a primary key column to the newly created table so as to ensure
       uniqueness
      Add a foreign key column to the new table. It should be the same column at
       the primary key in the base table.

To understand better, follow the example given.

Example

To arrive at a functionally efficient library database schema, you would have to
normalize the tables of the library database. The main table used in the library is
where the transaction details will be stored. You would require:

      All information pertaining to the customers who borrow books

      All information of the borrowed book, such as its author, its publisher‘s
       information and the dates of issue and return

      The un-normalized table is as follows 




© SQL Star International Ltd.                                                     17
© SQL Star International Ltd.   18
This table can be brought to the 1NF by removing all the repeating columns. The
repeating columns are put into separate tables in logical groups with a primary key
as a unique identifier for each table. The tables in the first normal form are:




Second Normal Form (2NF)

The second normal form can be defined as the level where tables are in the 1NF, and
where for every table, all its non-primary key columns are dependent on the whole
primary key. A column should not be partially dependent on the primary key. When a
column depends on part of the primary key it is called partial dependency.

To remove partial dependency:

   1. Identify the non-primary key columns and remove them from the tables

   2. Create another table to contain the removed columns, and the primary key column
      that they are dependent on.

To bring a table to the 2NF, any of the following rules should be met:

      The primary key column should not be a composite key. That is, it should be
       made up of only one column.

      All the non-primary key columns are dependant only on the primary key.

      There should be no non-primary key dependent columns in the table.

To bring the tables to 2NF, remove all those columns that are partially dependent on
the whole primary key. For instance the book availability does not depend on the
transaction ID but only on the book ID. So that column can be removed into a new
table.

Hence, the tables in the second normal form will be as follows:



© SQL Star International Ltd.                                                      19
Third Normal Form (3NF)

The third normal form is defined as the level where the non-primary key columns in the
tables are directly dependent on the primary key and are not dependent on any other non-
primary key. If you remove the transitive dependencies from a table in 2NF, then it is
said that, “the non-primary key columns are dependent on the primary key, the whole key
and nothing but the key”.




Steps to convert a table to the third normal form are:

       1.     Identify the non-primary key columns that depend on other non-
              primary key columns.

       2.     Remove the columns arrived at in the first step from the base table.

       3.     Create another table with the removed columns and include the
              non-primary key column that they are dependent on making it the
              primary key.

       4.     Create a foreign key in the base table linking it to the primary key in the
              new table.

© SQL Star International Ltd.                                                         20
To bring the tables to their third normal form remove the non-primary keys that are
dependent on other non-primary keys and also remove the columns that are
calculated or derived columns. The membership fee a non-key column depends on
the age of a member, which is another non-key column. Tables in the third normal
form are:




The Entity Relationship Model
The conceptual level model is a very important model in typical database
architecture. To represent or model data at this level, three major data models
namely, network, hierarchical and relational, have been proposed which you shall
examine later. Each of these models has its own pros and cons. The entity
relationship model is not a formal data model, unlike the three mentioned above.
However, this model is a more natural view of the real world, which consists of
entities and relationships, as you shall see shortly. Therefore, this model is very
useful for understanding the concept of data modeling. The three formal models
employ certain ways of representing data known as data structures; essentially to
represent the ―entity relationships‖ existing in the real world.

The entity relationship model (E-R model) clarifies concepts regarding what entity
relationships are, and what modeling entity relationships existing in the real world
means. Therefore, a study of the E-R model should be an appropriate first step
towards understanding the three major data models.



© SQL Star International Ltd.                                                          21
Entities
An entity is a thing, which can be distinctly identified. What is important over here is
that it is individually distinct. Employees, a house, a supplier to an organization, are
all entities. Identification of entities relevant to a database is extremely important,
because, a database contains data about entities.

All entities of the same type form an entity set. ―All Employees‖ form an entity set
and so do ‗All Suppliers‘.

Distinguishing Entities
As has been stated, an entity is a distinctly identifiable thing. To distinguish one
entity or one member of an entity set from another, one needs some means of
distinction. This distinction is achieved through values of what is known as the ―Key
Attribute‖ of the entity.

The database gives information about different entities contained in it. This
information is about different properties of each entity. For example, a personal
database contains information about employees (here employee is the entity). The
properties of an employee about which information is given, may typically be,
employee number, name, date of birth, date of joining the organization, total job
experience and educational qualifications. Each of these properties is called an
attribute of the entity.

Each of the attributes can take on a value from a range of possible values, which is
known as the domain of values for that attribute. The values need not be only
numerical but may also be character strings.

For each entity in an entity set, there is an attribute, which distinguishes the entity
uniquely from the other members of the set. This attribute is the key attribute for
the entity-set. For example, the employee entity-set discussed about can have either
the employee number or the employee name (assuming no two names are identical)
as the key attribute. In some cases, a combination of more than one attribute may
act as a key, instead of just one key attribute. Some times, an arbitrary serial
number may have to be supplied as the key attribute.

There are special cases where the members of an entity-set can be distinguished
from one another only by their relationship to entities of another type. The ‗is a‘
relationship is one such relationship. These cases will be illustrated when we take up
an actual example of an E-R model later.

Relationships
In a real-world situation, certain entities are associated with each other. For
example, referring to the employee entity-set will have a relationship with the
department entity-set signifying the department for which an employee works. This
relationship can be expressed as the ―works-for‖ relationship from ―employee‖ to
―department‖.

A relationship may exist amongst the members of the same entity-set. For example,
in the employee entity-set, some employees may be seniors of certain other
employees. Therefore a relationship ―senior-of‖ may exist between one member of
the employee entity-set and a few other members of the same set.



© SQL Star International Ltd.                                                        22
A diagrammatic representation for the employee-department relationship may be as
given below.




A diagrammatic representation for the ―senior-of‖ relationship may be:




It should be noted that relationships convey very important information regarding
the relevant real world situation just as entities do, and hence should be properly
represented.

There may also be relationships involving more than two entity sets. For example,
Prof. Smith teaching Economics to a student named Sam. This relationship contains
two relationships – (1) Prof. Smith teaches Economics and (2) Prof. Smith teaches
Sam. These two relationships cannot be combined to deduce the information given
by the original relationship.

The same entity-sets may be also linked by more than one relationship. For
example, the Professors and the Students entity-sets may be linked by the two
relationships, viz; (1) TEACHES and (2) ADVISOR-O

Types of Relationship
Relationships between the entity-sets can be classified according to how many
members of one entity-sets are related to one member of the other entity-set and
vice-versa. Accordingly, the following types of relationships can be identified.

One-to-One Relationships
If a one-to-one relationship exists between two entity-sets A and B, it means that
with each entity in A, at most one entity in B is associated and vice-versa. Strict
one-to-one relationships are not very common in real world situations. Consider an
entity set of traffic policemen and another entity-set of traffic control points in the
city and assume that only one policeman controls one traffic control point. Under this
assumption, the relationship CONTROLS between the entity sets POLICEMEN and
CONTROL-SITES will be a one-to-one relationship.

Many-to-one Relationships
This type of relationship is quite common in everyday life. If, with each entity in the
entity-set B, zero or more entities in set A are associated, then we say that a

© SQL Star International Ltd.                                                         23
many-to-one relationship exists from set A to set B. In our earlier employee
database example, the WORKS-FOR relationship is a many-to-one relationship from
the entity-set EMPLOYEES to the entity-set DEPARTMENTS (assuming that an
employee works for only one department at a time).

Many-to-Many Relationships
This is yet another type of relationship which is quite common in real-life situations.
In this case, associated with each entity in set A, there may be zero or more entities
in set B and vice-versa. A very common example of this type would be the
relationship between the entity-set SUPPLIERS and the entity-set PARTS. A supplier
may supply many parts, while a part may be supplied by many suppliers.

Guidelines for Constructing the Entity-Relationship Model
Having understood the basic components, you are now in a position to consider the
construction of an E-R model. The principal steps involved in this exercise are:

   •   Select relevant entity-sets for the real-life situation under consideration

   •   Select relevant attributes for each entity-set

   •   Identify the key-attribute for each entity-set

   •   Determine the type of each of the relationships between the entity sets

   •   Draw the E-R diagram

Consider the situation in which the academic administration often finds itself. It has
to handle data regarding students, faculty, and the courses being offered, and
possible areas of specialization. It is worthwhile to consider the following points
before you move to construct the model:

   •   The students specialize in one or more areas

   •   The students study a specific course

   •   A course belongs to an area of specialization

   •   A faculty member belongs to an area of specialization

   •   A student can be either a doctoral student or a degree student

   •   A faculty member guides a doctoral student

   •   Certain courses have certain other courses as prerequisite

   •   A faculty member offers a specific course

From the above, the desirable entity-sets, their relevant attributes and the
appropriate key attributes can be determined.

  1.   Entity-set : Students
       Attributes : Roll No, Name, Date-of-birth, Basic Educational
       Qualification, No. of years of work experience

© SQL Star International Ltd.                                                        24
Key       : Roll No.

  2.   Entity-set : Faculty-members
       Attributes : Name, Date-of-birth, Date of Joining, Educational
       Qualifications, Total No. of years of Teaching Experience
       Key        : Name

  3.   Entity-set : Courses
       Attributes : Course-No, Course-Name
       Key        : Course-No

  4.   Entity-Set : Areas (of specialization)
       Attributes : Name of the Area
       Key         : Name of the Area

  5.   Entity-Set : Doctoral-students
       Attributes : None

This entity-set is needed to identify individual doctoral students. The reason for
assigning a separate entity-set to doctoral students is to be able to establish the
relationship between these students and their faculty guides, in the actual database.

Now you are in a position to identify the different relationships amongst the above
entities. These are:

       1. SPECIALISES_IN: This is a many-to-many relationship between STUDENTS
       and AREAS

       2. STUDIES: This is a many-to-many relationship between STUDENTS and
       COURSES

       3. INCLUDED_IN: This is a many-to-one relationship from COURSES to AREAS

       4. BELONGS_TO: This is a many-to-one relationship from FACULTIES to
       AREAS

       5. GUIDES: This is a        one-to-many    relationship   from   FACULTIES   to
       DOCTORAL- STUDENTS

       6. OFFERS: This is a many-to-many relationship from FACULTIES to
       COURSES. The assumption here is that a course may be offered by more than
       one faculty-member

       7. IS A: This relationship is one-to-one between STUDENTS &
        DOCTORAL-STUDENTS

       8. PREREQUISITE_FOR: This is a many-to-many relationship from COURSES
       to COURSES because a course may be a prerequisite for more than one other
       course and may have more than one other course as prerequisites for itself

Now you are ready to draw the E-R diagram representing the E-R model. First let us
discuss the relevant diagrammatic conventions and then actually draw the diagram




© SQL Star International Ltd.                                                       25
Conventions for Drawing E-R Diagrams
Following are the conventions for drawing E-R diagrams:

   ·   Entity-sets are represented by rectangles.

   ·   Attributes are represented by circles. These are linked to the appropriate
       entity-sets by undirected edges.

   ·   Relationships are represented by diamond shaped boxes. These are linked to
       the appropriate entity-sets by directed edges.

An E-R diagram for the Academic Administration database is:




As already stated earlier, the E-R model brings out the essential features of data
modeling for databases. Data modeling in practice, is done according to the one of
the three models, viz., hierarchical, network and relational. The three models too,
establish relevant entities and the relationships amongst them; they differ in the way
they represent data about both entities and their relationships. The E-R model,
however, is free from these relatively physical aspects of data representation and
therefore can be said to be a general view of the three models unifying them at a
relatively abstract level.

Case Study – Entity Relationship for a Library
The library needs to create a database to automate its data storage and processes.
For this you first need to know how a library functions, what are its transactions and
what data it needs to store for activities. To arrive at an ERD for a library, list the
entities and its attributes you require before putting them into a diagram:

      Member

             Member ID

             Name

© SQL Star International Ltd.                                                       26
   Address

             Area

             Zipcode

             phone number

             Age

             Date of membership

             Age group

             Branch ID



      Book

             Book ID

             Book name

             Author name

             Publisher

             Published Year

             Category

             Branch

             No of copies in store

      Transaction

             Transaction ID

             Member ID

             Book ID

             Issue date

             Return date

             The actual return date

             Fine to be paid by the member for default

    Category (for books)

             Category ID
© SQL Star International Ltd.                             27
Category description

       MemberFee

                Age group grade

                Minimum value

                Maximum value

                Fee amount

       Branch

                Branch ID

                Branch name

                Address

                Location

                Phone number

                Date of establishment

                Availability

                Book id

                Available copies

      Publisher

                Publisher Id

                Name

                Address

The list arrived at above can be depicted as an ERD in the following manner:




© SQL Star International Ltd.                                                  28
Communicating with RDBMS

In order to communicate with the RDBMS, that is, to access data, you have a query
language called a Structured Query Language (SQL). A query can be defined as a
request made to access data from the database. This definition refers not only to
data retrieval, but also defining, manipulating and controlling data. The need to
access data from the database on an ad-hoc basis led to the origin of SQL. The origin
of SQL can also be associated with one of Codd‘s Twelve Rules, where in he states
that a relational database must have a high level language capable of handling all
communication with the database. Although there are several languages that can
access data from the database, SQL is the primary language for communicating with
RDBMS. SQL can also operate on non-relational databases.


© SQL Star International Ltd.                                                     29
Features of SQL
The features of SQL are as follows:

     •    SQL is a Declarative Language (non-procedural). You need not provide the
          Step wise procedure to be followed in order to access the data. Instead, it
          allows you to simply declare what data you want without having to provide
          details about where it is located or how to get it. It leaves it to the DBMS to
          determine the best way to get it.

          On the contrary, procedural languages such as C, or C++ provide a step-wise
          procedure telling the computer exactly what is to be done. The advantage
          being that these instructions given ahead of time can be compiled into
          machine language for fast execution. But these languages lack flexibility, that
          is, do not adapt to changes easily.


     •    SQL is a set-based language. Since the relational model uses the concept of a
          mathematical relation that is, has its theoretical basis in set theory, SQL
          supports set operations and relational algebra operations.


A set is an unordered collection of elements of the same type and structure. Tables
(or relations) are called sets and rows (or records) are their elements. In a relational
database the physical positioning of rows is not important, that is, they are
unordered, so SQL being a set-based language can operate on an entire table, or
multiple tables at once. In contrast, a procedural language can operate on a single
record at a time as it uses ‗files‘ which are similar to tables, wherein records have a
physical ordering.

Relational algebra operations can be divided into two groups:

 Set operations from mathematical set theories including Union, Intersection
             and Set Difference.

 Operations developed for relational databases, which include Select, Project
             and Join.



Set Operations
Set operations include the following:

 Union

 Intersection

© SQL Star International Ltd.                                                         30
 Set Difference



Union

To understand the union operation look at the following two tables, States1 and States2:




The above two tables contain names of US states. Some of the state names are
common in both the tables.
In order to return the state names that are in States1 or in States2 or in both
States1 and States2, eliminating duplicate rows, you use the UNION operation.
The notation for union of tables is:
States1 UNION States2 = States3
The result of the union operation is as follows:



                                      States 3
                                        Hawaii
                                     New Jersey
                                       Indiana
                                       Florida
                                       Arizona
                                      Colorado
                                      California
                                        Alaska
                                        Texas
                                       Georgia
                                       Virginia
                                     Wisconsin
                                       Kansas
                                      Kentucky
                                         Iowa


The resulting table contains the state names that are contained in both the tables,
but displaying the common state names only once.




© SQL Star International Ltd.                                                         31
Intersection
The intersection operation returns state names that are in both States1 and
States2, that is, it returns a third table that contains only common state names.
The notation for intersection of tables is:
        States1 INTERSECTION States2 = States3
The result of the intersection operation is as follows:




Set Difference

The result of the set difference operation returns state names that occur in the
States1 table but not in the States2 table, or also vice versa. The result is as
follows:




Relational Operations
In addition to set operations, certain other operations were developed for relational
databases, which include:

      Selection

      Projection

      Joins



Selection
The selection operation enables you to retrieve only specific rows that match your
criteria. For example, you have two tables TabA and TabB.




© SQL Star International Ltd.                                                     32
Using the selection capability of SQL, you can retrieve those rows from TabB table
where Col1 value is 2.
The result set of rows would be:




Projection
The projection operation enables you to retrieve only specific columns from the total
columns available. For instance, using the projection capability of SQL, you can
retrieve only Col2 values from TabA table.
The result set would be:




Joins

The join operation enables you to retrieve data from more than one table. For
instance, using the joining capability of SQL, retrieve rows from both TabA and
TabB by joining Col1 as they have equivalent values.
The result set of joining the two tables would be:




Why SQL is Preferred?
SQL is favored due to the following reasons:


© SQL Star International Ltd.                                                     33
   A wide range of users, including those with little or no programming
        knowledge can use it.

      It is an English-like language.

      It is non procedural, that is, the user need not specify the method to be
        followed to arrive at the result, rather just specify the result that needs to be
        arrived at.

      It allows defining, retrieving and manipulating data in the tables.




Relational Data Model Concept
This rule states that all data is represented as tables. Data can be viewed in no other
way.



Codd’s Rules
Dr. E. F. Codd, was the creator of the relational data model. It was published as a two-
part article in ComputerWorld (Codd, 1985). It contains a list of 12 rules that determine
whether a DBMS is relational and to what extent it is relational. These rules are a very
useful yardstick for evaluating a relational system. In the article, Codd mentions that
according to these rules, there is no database yet that is fully a relational system. He says
that rules 6, 9, 10, 11 and 12 are difficult to satisfy. Each of the twelve rules is briefly
discussed below.


The Information Rule

All information in a relational database is represented explicitly at the logical level and in
exactly one way through values in tables.


Guaranteed Access Rule
Each data item must be accessible by providing table name + primary key of the row
+ column name.


© SQL Star International Ltd.                                                              34
Systematic Treatment of Null Values
Handle missing or non-applicable data, that is, nulls, in a consistent manner. Nulls
should have no values and should simply be missing data. Treating Null as a zero for
missing numeric data or as a blank for missing character data violates this rule.
Vendors provide the ability to use default values for missing data, if so desired.

Self-describing Database
In addition to storing user data, a relational database must contain data about itself.
There are two types of tables in RDBMS: user tables, which contain data required by
users, and system tables, which contain data about the database structure. The data
that describes the database structure is called meta-data. The collection of system
tables is called as the system catalog or data dictionary. Storing any part of the data
dictionary in operating system files would violate this rule.



Comprehensive Data Sublanguage
The data access language (SQL) must be the only means of accessing data stored in
the database. The language must support relational operations and set operations
with regard to the following:

      Data definition

      Data manipulation

      Integrity definition

      Transaction control

      Data control

Accessing data files (files that contain the actual data), through a utility other than
an SQL interface, violates this rule.



View Updating Rule
There are situations where users may require only a part of the table information or
information from a collection of tables. Such requirements can be met by creating
‗Views‘. Views are virtual tables, which unlike a table contains no data, just
statements that return data in the form of tables.
This rule states that views should allow updates in the underlying tables and vice
versa.
But SQL supports only updates of single tables at a time (see rule 7), therefore if,
you join three tables to create a view, and try to update that view, then DBMS would
fail to translate these updates to the underlying tables, thereby violating this rule.
Also, a view not including the column that uniquely identifies each record in a table
cannot be updated, thus violating the rule.
This rule will be dealt in depth in the chapter on ―Views‖.

High-level Insert, Update and Delete
This rule states that in a relational database, the query language (SQL) must be
capable of performing manipulations (such as, inserting, updating or deleting data)
© SQL Star International Ltd.                                                       35
on sets of rows in a table. A database that supports only row-at-a-time manipulation
cannot be considered as relational.

Physical Data Independence
This rule states that in a relational database, any changes made in the way data is
physically stored (that is, data stored in file systems specific to the machines
operating system) must not affect applications that access data. If a file supporting a
table was moved from one disk to another or renamed, then this should have no
impact on the application.

Logical Data Independence
This rule states that changes to the database design should be done in a way without
the users being aware of it. The change could be to expand the database (adding a
new table) or to reduce it, but the application that refers to the data (logical) must
work as before. If a single table were split into two, then a view would have to be
provided joining the two back together so that there would be no impact on the
application.



Integrity Independence
In order to be considered as a relational database, all data integrity, which are
definable in the query language referred to in rule 5 must be stored in the database
as data in tables, that is, in the catalog and not in the application programs.

The data integrity rules that should apply to relational databases are:

       Entity integrity- the primary key column cannot have missing values

       Referential integrity- for every foreign key column value there must exist a
       matching primary key column value.

       Integrity rules are covered in depth in a later chapter.



Distribution Independence
In a relational database, data can be stored centrally (on a single system) or
distributed (across a network of systems). The data in a centralized database should
remain logically unaffected if they are distributed across systems. For example, a
user should be able to retrieve data from two tables distributed across two terminals,
the same way, as they would retrieve them if stored in the same terminal.

Non-subversion Rule
This rule states that there should be no other access path to the database, other
than SQL. Any other access language may bypass (or subvert) security or integrity
rules, which otherwise would be obeyed by the regular data access language.




© SQL Star International Ltd.                                                         36
Summary
In this chapter, you have learnt that:

   Files prove to be inefficient due to their redundant nature when the number of
     applications increase. This gave rise to the concept of Database.

   Database is a collection of logically related data stored on media.

   To handle and maintain this database, a software, Database Management
     System (DBMS) came into existence.

       They are of 4 types:

          1. Hierarchical Database Management System

          2. Network Database Management System

          3. Relational Database Management System

          4. Object Relational Database Management System

    Out of these types, Relational Database Management System (RDBMS) was
     popularly used which enables to relate data in one table to the data in
     another.

   Normalization is the process to stabilize a database, by reducing data
     redundancy.

   Data can be stabilized through 3 stages:

          1. First Normal Form (1NF)

     2. Second Normal Form (2NF)

          3. Third Normal Form (3NF)

   To access the stabilized data, Structured Query Language (SQL) is widely
     used.




© SQL Star International Ltd.                                                   37
Lab Exercise
In the following questions, you are given the Universe of Discourse
(UOD, that is, the general outline at the level a user would normally
describe) of some typical enterprises. Please note that a UOD is not
a smooth and structured description.

Define:

      Entity and associated attributes

      Relationships between entities and type of relations

      Draw the Entity-Relationship diagram

1. LIBRARY SYSTEM:
A library keeps records of current loans of books to borrowers. Each borrower is
identified by a borrower number and each copy of a book by an accession number.
The name and address of each borrower is held so that overdue loan reminders etc.,
can be sent whenever necessary. The information required about books is the title,
authors, publishers, publication date, International Standard Book Number (ISBN),
purchase and price and current price. There is a restriction on the number of books
a borrower may have on loan at any one time, the limit depending on whether a
borrower is classified as having junior or adult status. Books out on loan may be
reserved by other borrowers pending their return. The library stocks only the
hardback version of the book. If a new edition of the book is published, all copies of
earlier editions are withdrawn from stock.

2. A UNIVERSITY:
A University has number of departments. Each department has its faculty.
Departments enroll students.
Each faculty member may conduct one or more courses and one or more students
register for a course. The courses are conducted in classrooms based on a prepared
time-table.
Each subject has a prescribed text book and host of recommended reference books.

A faculty member may guide more than one project and the same project may be
done by more than one student.

3. DEPARTMENTAL STORE:
The data in the database of a department store are defined as follows:

      Each employee is represented. The data about an employee are his employee
        number, name, address and the department he works for.

      Each department is represented. The data about departments are its
        employees, manager and items sold.

      Each item sold is represented. The data about items are its name,
        manufacturer, price, model number (assigned by the manufacturer) and an
        internal item number (assigned by the store).

© SQL Star International Ltd.                                                      38
   Each manufacturer is represented. The data about a manufacturer are its
        name, address, items supplied to the store and their prices. Various
        employees work for a department and each department stores items supplied
        by various manufacturers.



A MANUFACTURING ENTERPRISE:
A manufacturing company consists of a number of divisions. Each division, in turn,
consists of one or more departments. Each employee of the company belongs to
only one department at any point of time. Orders are executed at the divisional level.
Any number of departments (as required) may execute an order. A department may
also execute a number of orders.       Employees work on various orders in the
organization.

An order needs several parts. A part may be needed by several orders. A part itself
may consist of sub parts. Alternatively, a part may be a support of a super part.
Parts are housed in warehouses which are at specific locations. Suppliers supply
parts.

AN AIRLINES ENTERPRISE:
An Airlines company has a fleet of aircraft‘s which it employs to carry passengers
from one airport to another.

A flight (i.e. an aircraft assigned for trip from one airport to another) is manned by a
crew. A time table is available for all the flights. At each airport, based on the flight
schedules, service schedules are drawn up for the ground staff.

At each airport, for each flight, caterer(s) provide the necessary food and
refreshments according to the catering schedule.

The maintenance of aircraft‘s (that are not in operation and which have been tagged
for maintenance) is done by the maintenance staff according to the maintenance
schedule. Maintenance is conducted at the airports where hangar(s) are available for
the type of aircraft in question.




© SQL Star International Ltd.                                                         39
Chapter 2


                                Introduction to Oracle10g
                                          Key features of Oracle10g
                                          Components of Oracle10g




© SQL Star International Ltd.                                   40
Objectives
At the end of the chapter, you will be able to:

              Identify the different components of Oracle10g

              Identify the enhanced features of Oracle10g




© SQL Star International Ltd.                                   41
Introduction
The traditional database systems such as relational, hierarchical and network have
been successful in developing the database for traditional business applications such
as banking and railway reservations. But, when it comes to more complex business
applications such as databases for scientific work, engineering designs,
telecommunications, geographic information system and multimedia, the traditional
database systems cannot handle them because the requirements and characteristics
of these applications are different from the traditional business applications. These
applications require more complex structures for:

      Storing data related to real world objects such as engineering diagrams,
       molecular structures, or financial instruments

      Transactions, which would be for longer durations

      New data types required for storing complex multimedia data such as audio
       and video clips, images and maps.

Oracle10g Database meets the above needs as it tightly incorporates ORDBMs
concepts.
Object Relational Database Management System (ORDBMS) is a database
management system that has evolved from the relational model and includes both
the relational and object-oriented technology. Oracle8.0 was the first version of the
Oracle database to incorporate object-oriented technology.

In Oracle10g, ‗g‘ stands for GRID. This release is focused on efficient management of
infrastructure based on its grid computing mechanism.
Now, the question arises what is Grid Computing?

The idea behind the grid computing is to utilize the resources available, to the
maximum extent by dynamically pooling it based on the requirement of the end user
during the peak hours. In this case, the end user need not know the whereabouts of
the resource.

Infrastructure Advantages

Data Availability
Internet database availability is critical for any eBusiness application. Oracle10g
focuses on the following areas to achieve continuous data availability:

      Zero data loss data protection environment

      Support for online reorganization and redefinition architecture to reduce
       offline maintenance requirements

      Provides more complete and precise database repair capabilities by ensuring
       better prevention and improved handling of disk corruption



© SQL Star International Ltd.                                                     42
Scalability and Performance
Oracle10g enables eBusiness to scale millions of users performing millions of
transactions per hour by focusing on the following key areas:

 Transparent cluster scalability and performance: Oracle10g along with its
grid mechanism includes Real Application Clusters (RAC) that has been designed to
provide continuous data availability while increasing the scalability and performance
of the database infrastructure. RAC was introduced in Oracle9i, which is an
arrangement, where a single database runs on a group of servers that are clustered
together. With Oracle9i RAC all servers in the cluster act as backup to each other
while at the same time increasing the overall computing power within the cluster.

 Scalable session state management: Oracle10g allows more users to be
hosted on the same or larger hardware platforms due to its new grid mechanism
where in new nodes can be added to the cluster when the load increased.

 Optimized features critical for eBusiness: Oracle10g focuses on the following
performance areas, critical for eBusiness:

       Support for large datafiles. Enterprises planning to setup Data Warehouse
            and transaction systems can extend their Oracle database upto 8
            Exabytes, which is equivalent to 8 million terabytes.

          Improving the performance of many of today‘s business applications by
           providing support for enhanced native compilation and improved
           optimization of PL/SQL.

          Improving optimization plans and reducing resource usage by adding
           memory and CPU costs to the cost based optimizer cost calculation
           algorithm

          Improving performance in Data Warehouse and Online Transaction
           Processing (OLTP) environments by general I/O improvements such as
           better sharing of run-time data structures, larger buffer caches and
           deferrable constraints.

Security

Oracle10g provides secure          application   development      and   deployment
platform by focusing on:

A strong three-tier security, which ensures that a user can access the database
only through the middle tier. As a result user identities are maintained securely
through all tiers of an application, with centralized user and privilege management in
Oracle Internet Directory.

Deep data protection through enhancements in Virtual Private Database, fine-grained
auditing and Oracle Label Security

Development Platform for eBusiness Applications

Oracle10g continues to provide the best development platform for both eBusiness
and traditional application development by focusing on the following key area

© SQL Star International Ltd.                                                      43
   Enterprise Java Engine:

Java support in Oracle10g focuses on improving the performance of the embedded
Java Virtual Machine, new JDBC and SQLJ functionalities, and enhancement to Java
stored procedures.

 SQL and PL/SQL improvements:

Oracle10g has introduced many enhancements in SQL and PL/SQL to meet modern
development requirements. Oracle10g supports inheritance, type evolution, and
dynamic method dispatch to increase the usefulness of objects. Along with the
existing datatypes, new datatypes have been introduced. It also supports CASE
statement, ANSI compliant joins and reserved naming conventions.

           New Dataypes

           In addition to the existing datatypes, new datatypes have been
           introduced. They are BINARY FLOAT and BINARY DOUBLE. Bioinformatics
           and life science applications have benefited from these datatypes to solve
           complex computations.

            Alternative Quote operator:

          Strings containing single code as literal, can be now be escaped using
          customized symbols using Q operator.

           Environmental Scripts after each CONNECT:

          Previously glogin.sql and login.sql scripts were read at the startup of
          iSQL*Plus. Now, these scripts are automatically run after each user
          connects to the database.

           Multiple Pages Output:

          Output spanning over multiple pages can now be viewed using NEXT
          button or can be viewed on a single page as in the previous version.

          SQLPlus Recycle Bin:
          SHOW RECYCLEBIN [original_name] command has been introduced to
          view the dropped database objects.

         Oracle Flashback Feature:

          This feature has helped a developer to reduce errors.

                  Oracle Flashback Table:
           FLASHBACK TABLE statement in SQL allows to recover the accidentally
           dropped table.


                  PURGE TABLE:
          This statement removes the database objects permanently from the
          Recycle Bin.


© SQL Star International Ltd.                                                     44
Oracle Flashback

Version Query
Changes in the table data can be viewed using VERSION            BETWEEN clause. A
changed transaction‟s undo records stored in the database must be available.

Oracle Flashback Transaction Query
    Changes made to the tables can be viewed using
    FLASHBACK_TRANSACTION_QUERY view. This can be helpful for auditing,
    debugging and even performance analysis.

Improved MERGE Functionality
    MERGE Statement has been improved by making WHEN MATCHED and WHEN
    NOT MATCHED clauses optional. Also, WHERE clause can now be used in this
    statement to restrict the values while inserting into target table.

 Regular Expression functions:
    Regular Expression functions have been introduced which works beyond the
    POSIX (Portable Operating System For UNIX) standard for matching ASCII
    characters.

Improvements to PL/SQL:

     Bulk Binding Enhancements:
    Performance related to BULK BINDING has been enhanced by introducing
    INDICES OF and VALUES OF clauses. INDICES OF clause permits sparse data in a
    collection. VALUES OF clause refers one array values based on another array
    values.

   Enhanced Native Compilation:
    The number of parameters to be set for Native Compilation has been reduced. A
    much more tight integration of SQL and PL/SQL runtime engines is made
    possible.

   New Packages:

         DBMS_WARNING: Warnings generated during          compile   time   can   be
         dynamically set using DBMS_WARNING package.

         UTL_MAIL: This is an enhancement to UTL_SMTP package. Using this, E-
         mails can be sent through a PL/SQL API.

         UTL_COMPRESS: This package compresses and uncompressed RAW Byte
         stream of Large Object (LOB) data.

         DBMS_METADATA: This package extracts the metadata of a database
         object, which can be obtained either in XML version or DDL.




© SQL Star International Ltd.                                                    45
   CLOB and NCLOB Implicit Conversions:

          You no longer need APIs to convert CLOB to NCLOB and vice versa. This
          release supports their implicit conversion.

Oracle10g and the Internet
Oracle8i was the first internet-based database in the world. It recognized that
Internet provided the safest and efficient access to data to all users spread across
the globe.

Oracle10g continues the Oracle9i focus on the Internet by providing a series of
enhancements targeted at eBusiness environments.
To be able to allow commerce on the net, your system needs some important
hardware configuration so that it can support the transactions between the database
and the Internet. One important step is to identify the kind of machines that you
need.

Fat client or Thin client

There are two kinds of client available, fat client and a thin client. Before debating
whether everybody needs a fat client or a thin client, you need to understand what
these terms mean.

A fat client is a traditional PC system, which if purchased today would have 64MB or
more of memory, 6GB or more of disk space, a fast paced processor and/or a CD-
ROM drive. A fat client would have all the codes locally within them.
A thin client is a personal computer used mainly for functions like e-mail,
presentation of information and word processing. It stores no code/programs locally
and only accesses them from the database.

The reasons for shift from fat clients to thin clients are due to the following
limitations:



       Loss of critical pieces of information if they reside only on a disk drive in the
         event of a break down

       The need for upgrading the software every time a new version comes into the
         market. This raises a lot of questions. Should the release of new versions
         force the end users to upgrade their software? Whether to assume that end-
         users have the necessary skills to upgrade their software? Should the
         support people go out to hundreds of PCs and upgrade them individually?
         Isn‘t this a waste of their time when these activities are only for someone who
         uses e-mail?

The above complexities of fat client led to the development of a more mature
network known as the Network Computing Architecture (NCA) wherein the end user
would not be required to deal with issues like loss of data due to virus attacks or deal


© SQL Star International Ltd.                                                          46
with upgradations. Trained professionals would handle these at some central
location.


Oracle Internet Platform

The positioning of Oracle as an Internet solution company is due to the adoption of
NCA. This architecture enables the development, deployment and integration of
applications within a networked computing environment. Oracle has developed NCA,
which is based on the following three separate tiers:

      A thin client tier, which is the layer responsible for the presentation of the
        information. It is the desktop PC running a web browser.
   
      An application server tier (the middle tier), which is the layer wherein all the
        application codes are processed.
   
      A database server tier, which is the layer where all the data is stored.




                           A Three-tier Architecture


The NCA is designed such that the presentation layer is separated from the
application layer. The application layer resides on a server separate from the
database server and it is assumed that the application server is the fat client. The
application server as well as the database server can be moved to a machine with
more resources, which could be placed in a central location and be managed by
trained professionals thereby keeping the end users away from all the complexities.

Based on the above theoretical concepts, Oracle 10g release is broadly divided into:

         • Oracle Database 10g

         • Oracle Application Server 10g

© SQL Star International Ltd.                                                        47
• Oracle Enterprise Manager 10g Grid Control

• Oracle Database 10g

Oracle10g database supports Grid Computing architecture. Here, multiple database
servers are pooled together to form a cluster. It enhances utilization of resources. It
efficiently stores and manages the structured and unstructured data such as:

         • Spreadsheets

         • Word documents

         • PowerPoint presentations

         • XML

         • Multimedia data types like MP3, graphics, video and more.

Oracle 10g facilitates two-tiered or multi-layered distributed database environments
like client/server and Web-based applications. Large objects need be stored inside
and outside the database. Oracle Database 10g has services which help to manage
and retrieve data, located outside the database.

• Oracle Application Server 10g
A complete infrastructural platform is provided for developing and deploying
enterprise applications, integrating many functions including a J2EE and Web
services run-time environment, an enterprise portal, an enterprise integration
broker, business intelligence, Web caching, and identity management services. The
existing 9iAS gets further enhanced with the introduction of new grid computing
features. It further integrates users, applications and data across your organization.


• Oracle Enterprise Manager 10g Grid Control
It is the consolidated, core management console that forms the basic framework to
automatically initiate administrative tasks across the networked environment. With
Oracle Grid Control, multiple hardware nodes, databases, application servers and
other targets can be brought together into single logical entities.



Oracle10g continues Oracle Corporation’s lead on providing the best platform support
for business intelligence by focusing on the challenges raised by large volume of data
and the need for real time complex analysis in an eBusiness environment. Oracle10g
provides the business intelligence platform by enhancing and extending database
support for Online Analytical Processing (OLAP), data mining and extraction.




© SQL Star International Ltd.                                                        48
Summary
In this chapter, you have learnt that:

    In Oracle10g, ‗g‘ stands for GRID. It is a technology, which groups similar
   resources into a cluster. This allows efficient utilization of resources. This helps
   us to design complex business applications.

    Data availability, security and development for e-business applications are
   some of the advantages with Oracle10g.

    Oracle10g structure is based on NCA (Networked Computing Architecture),
   which is developed to overcome the problems with fat client. It enables
   development of applications within networked computing environment.

    Oracle10g has come up with new features in SQL* Plus environment, new
   commands in SQL language and improvements in PL/SQL, making it more user
   friendly.




© SQL Star International Ltd.                                                       49
Chapter 3




                                                     Data Retrieval



                                                     iSQL*Plus Interface
                                 Logging into Database using iSQL*Plus
                              Projection, Selection and Join Terminology
                                Differences Between SQL and iSQL*Plus
                   Review of Syntaxes for Basic SQL SELECT statements
              Arithmetic and Concatenation Operators in SQL statements
                                              Alternative Quote Operator
                                  Saving SQL Statements to Script Files




© SQL Star International Ltd.                                        50
Objectives


At the end of this chapter, you will be able to:

           Use the SELECT statement to extract data
     
           Understand the various categories of SQL statements




© SQL Star International Ltd.                                      51
Retrieving Data
Oracle uses the Structured Query Language (SQL) to communicate with the
database. The SQL statement used to extract data from the database is the SELECT
statement. The SELECT statement informs the database about the data you want to
retrieve. SQL statements need to be executed in an environment where, they would
be interpreted and sent to database.

iSQL*Plus Environment



iSQL*Plus introduced in Oracle9i is a browser environment in which SQL statements
are executed. SQL*Plus environment was the default environment in the prior
releases of Oracle. SQL*Plus is still available.

Since the Oracle server understands only SQL worded statements, all Oracle tools
support SQL syntax. Implementation of SQL through SQL*Plus environment or
iSQL*Plus environment meets the ANSI (American National Standard Institute) and
ISO (International Standards Organization) standards.

On issuing an SQL statement, the statement first gets stored in a part of the
memory, which is called the SQL buffer. The SQL statements (stored in the buffer)
are then recognized and submitted to the Oracle database for execution by the
SQL*Plus or the iSQL*Plus environment.

The iSQL*Plus environment helps to perform the following tasks:

         Executing SQL statements to extract, add, change and remove data from
           the database

         Formatting and performing calculations on query results so as to produce
           more meaningful reports

         Storing SQL statements in files (called script files) so that they could be
           used later. These files have .sql file extension.




How to log in to SQL*Plus and iSQL*Plus?

The steps involved in logging into SQL*Plus and iSQL*Plus environments are
different.

Logging in to SQL*Plus Environment

Logging in to SQL*Plus environment depends on the type of operating system you
are working on.




© SQL Star International Ltd.                                                            52
Logging in through a Windows environment:
      1.Click Start-> Programs-> Oracle – OraDb10g_home1




       2. Select Application Development -> SQL Plus




© SQL Star International Ltd.                              53
3. Enter username, password and the connect string.




Logging in through a command-line environment:

        Log on to the DOS prompt
Enter SQL*Plus command as follows:

       sqlplus [username[/password[@ ConnectString]]]

Where,username is the database username assigned to each user.

password is the password the user enters to gain access to the database. The
password is visible on entering it at the command line. Therefore, to ensure the
integrity of the password, do not enter it at the command line. Instead enter it at the
password prompt.

@ ConnectString is the alias through which the user has to access the database.


Logging in to iSQL*Plus Environment
The steps to log in to iSQL*Plus environment are as follows:
   1. Initiate the browser and enter the URL address of the iSQL*Plus
      environment. iSQL*Plus browser window is displayed.


© SQL Star International Ltd.                                                       54
2. Enter the username and password as shown in the following screen.
      Click the
      Login button.




© SQL Star International Ltd.                                       55
After you log in to iSQL*Plus, you see the iSQL*Plus window as follows:




Within the windows browser, the key areas of the iSQL*Plus window are the:

     Enter Statements field: The area to enter the SQL statements and iSQL*Plus
     commands.

     Execute button: Click to execute the statements entered in the Enter
     Statements field.
     
     Load Script button: Click to access the area for entering the name and
     location of a file (containing the contents of the Enter Statements field, which
     has been saved) or the URL for the script you want to execute.
     Save Script button: Click to save the contents of the Enter Statements field to
     a file. It is suggested that you save these files with .sql extension.

     Cancel Button: Click to Cancel the query presently entered by the user. A
     confirmation is displayed at the end.

     Clear Screen button: Click to clear text from the Enter Statement field, output
     and stops any script running at that time.

     Help icon: Click to access iSQL*Plus help documentation.



© SQL Star International Ltd.                                                       56
iSQL*Plus Commands



iSQL*Plus has a set of commands, which are different from the SQL statements.
These commands need to be entered one line at a time. In order to continue a
command on the next line, end the current line with a hyphen (-).

iSQL*PLUS commands can be abbreviated. For instance, a command CLEAR BUFFER
could be written as CL BUFF. iSQL*Plus commands are not stored in the SQL buffer.

The main categories into which iSQL*Plus commands have been divided are:

         Environment – It affects the behavior of SQL statements for the session.

         Formatting – It formats the query output.

         File manipulation – It saves SQL statements into script files and, loads and
           runs them whenever needed.

         Execution – It sends SQL statements from the browser to the Oracle
           server.

         Editing – It modifies SQL statements in the Edit window.

         Interaction – It allows you to pass values into the SQL statements and
           also print messages to the screen.

SQL Vs iSQL*Plus
SQL is the language used to communicate with the Oracle server from any
tool or application. iSQL*Plus is the Oracle tool, which recognizes and
submits the SQL statements to the Oracle server for execution, and based
on the query result, it produces formatted reports using its own commands.

The following diagram depicts the SQL and iSQL*Plus interaction:




© SQL Star International Ltd.                                                       57
Browser             SQL Statements

                 iSQL*Plus                                              Oracle
                                                                        Server




           iSQL*Plus Commands                            Query Output


                                   Formatted Report


Features of SQL are:

         It is a non-procedural language of ANSI standard

         It is an English-like language

Features of iSQL*Plus are:

         It is accessible from a browser

         It supports ad hoc entry of statements

         It formats query output into a basic report

         It can access local as well as remote databases

         It controls environmental settings




© SQL Star International Ltd.                                                    58
SQL Statements
The SQL statements can be categorized with regard to their functionality.
They are:

         SELECT statements - used to retrieve data from the database.

       Data Definition Language (DDL)- used to create and maintain the
         database structure. The DDL statements are:

                CREATE

                ALTER

                DROP

                RENAME

                TRUNCATE




© SQL Star International Ltd.                                              59
 Data Manipulation Language (DML): used to manipulate data i.e. to add
         more data, update or remove data from the database.

      The DML statements are:

                INSERT

                UPDATE

                DELETE

                MERGE

       Transaction Control Statements: used to manage changes made by using
         the DML statements. The transaction control statements are:

                COMMIT

                ROLLBACK

                SAVEPOINT

       Data Control Language (DCL): used to secure the database. The DCL
         statements are:

                GRANT

                REVOKE

Features of a SELECT Statement

Using the SELECT statement, the following tasks can be achieved:

       Selection (or restriction): Using this feature you can retrieve only those
         rows in a table that you want the query to return.

          For example, a Manager may be interested in retrieving details of those
          employees who report to him. To selectively restrict retrieval of rows,
          there are SQL clauses, which will be covered in the subsequent chapter.

       Projection: Using this feature you can choose to retrieve only those
         columns in a table that meet your requirement.

          For example, an accountant would be interested in dealing only with the
          salary details of the company‘s employees. He would not choose to
          retrieve details such as their DOB, educational qualifications and their
          address.

       Join: Generally, (most of the time) data from more than one table is
         required to be retrieved. This task can be achieved by creating links
         between the tables from which data need to be retrieved and presented as
         combined data.

Basic Parts of a SELECT Statement

© SQL Star International Ltd.                                                         60
There are two parts that are mandatory in a SELECT statement. They are:

          The keyword SELECT (SELECT clause) followed by the columns that you
            want to see.

        The keyword FROM (FROM clause) followed by the table name from which
          the columns have been specified in the SELECT clause.
The syntax of a simple SELECT statement is

       SELECT {* | ,(column,)...}
       FROM table;

Where,
*(Asterisk) is used to select all the columns from a table

column is used to select those columns specified after the SELECT statement

table specifies the table from which the columns are to retrieved

 ; is the termination character. The SQL statements are executed immediately on
encountering this character.




Guidelines for Writing SQL Statements

There are certain rules and guidelines to be followed while constructing SQL
statements:

          SQL statements are not case sensitive.

          Enter SQL statements on one or more lines.

          Cannot split or abbreviate keywords.

          Place clauses on separate lines for better readability and editing.

          Typically enter all keywords in uppercase, tablename in Initcap and all the
            words following them, such as column names, in lowercase.

          At the end of the last clause place a semicolon (;).


Writing a SELECT Statement
© SQL Star International Ltd.                                                        61
Write SELECT statements to:

      Select all columns
      In order to retrieve all the columns from a table, you need to either place an
      asterisk (*) or list all the columns of the table after the SELECT keyword.

      For example, to retrieve all the columns from the Category table the following
      SELECT statement is issued in iSQL*Plus:

             SELECT * FROM CATEGORY;

      On issuing the statement, the following result is generated:




   --------------------------

   14 rows selected.

      

      Select specific columns
      In order to retrieve only specific columns of a table, you need to list the
      columns in the order that you want to see in the output.

      For example, to retrieve member’s last names, their age and membership
      dates the following SELECT statement is issued in iSQL*Plus:

             SELECT cLastName, nAge, dMembershipDt
             FROM Member;

      On issuing the statement, the following result is generated:




© SQL Star International Ltd.                                                    62
----------------
  21 rows selected.
From the query result you will observe that in iSQL*Plus:

         Default column heading justification is: Center

       Default column heading display is: Uppercase
On the contrary, in SQL*Plus (as shown below):

         Character and date column headings are justified to the left

         Number column headings are justified to the right

         Default column heading display is uppercase




© SQL Star International Ltd.                                             63
Refining Retrieved Data

On extracting data using the SELECT statement, you get the output exactly the way
it has been stored in the database. Oracle provides ways to refine retrieved data,
that is, to modify the way the data is displayed, by suppressing duplicate data
display, by performing some calculations or changing the column names.

Using the DISTINCT Keyword

The result of a request for data from a table would be without eliminating any
duplicate rows. To suppress duplicate rows use the DISTINCT keyword in the SELECT
clause.

For example, an attempt to retrieve book names from the Book table would result in
the retrieval of duplicate book names. This is because, the same books are stored in
all the branches of the New Jersey Central Library. Therefore, to retrieve the distinct
book names issue the following SELECT statement:

       SELECT DISTINCT cBookName
       FROM Book;

On issuing the statement, the following result is generated:




    ----------------
© SQL Star International Ltd.                                                       64
46 rows selected.

You can specify multiple columns after the DISTINCT keyword. It would
affect all the columns selected and return a distinct combination of the
columns selected.

For example, to retrieve unique combinations of the year of publish of books
and the book names, issue the following SELECT statement:

      SELECT DISTINCT dPublishedYr, cBookName
      FROM Book;




     ------------------------

 48 rows selected.

Using Arithmetic Operators



All the basic arithmetic operators are available in Oracle, thereby enabling
arithmetic calculations to be performed on the selected data.

                     List of Arithmetic Operators




© SQL Star International Ltd.                                            65
Arithmetic operators can be used in any clause of a SQL statement except
the FROM clause.

For example, suppose the library decides to see the result on incrementing
the number of copies of every book in each branch by two. This could be
done easily with the use of arithmetic operation as shown below:

       SELECT DISTINCT cBranchID, cBookName, nNoOfCopies, nNoOfCopies+2
       FROM Book;




---------------




--------------




--------------




--------------




181 rows selected

This example uses the addition operator to increase the number of copies of each
book. In the above result nNoOfCopies+2 is not a new column in the Book table. It is
just for display and by default gets the name from the calculation performed, which
in this case is nNoOfCopies+2. But this name is not very descriptive. Hence, Oracle
provides a way to rename column headings to make them more descriptive and
clear.

Renaming Column Headings
When you issue a SELECT statement, iSQL*Plus / SQL*Plus displays the column
headings, which are the same as the names of the columns selected. But, this
heading may not always be descriptive especially when calculations have been
performed. So, Oracle provides you the option to change the column headings by
using column aliases. By doing so, you can hide the business logic from others by
giving a descriptive name to the column specially during a calculation. Alias headings
appear in uppercase by default.

© SQL Star International Ltd.                                                      66
How to Define a Column Alias?

A column alias is defined as follows:

          In the SELECT list, specify the column alias immediately after the column
            name using the keyword ‗AS‘ or a space between the column name and
            the alias.

          Enclose the alias in double quotation marks (― ‖) if it contains spaces,
            special characters such as # or $, or if it needs to be case sensitive.


In the SELECT statement wherein you had performed an arithmetic calculation, by
default the heading of the column that displayed the calculated result was
nNoOfCopies+2. Give this column a more meaningful name by defining an alias as
follows:

      SELECT DISTINCT cBranchID, cBookName, nNoOfCopies, nNoOfCopies+2
            “Post Increment”
      FROM Book;

Displays:




------------------------------------
 184 rows selected.

In the above SELECT statement, the calculated column has been assigned an alias
without the use of the AS keyword. Whether the AS keyword is used or not, the
query result remains the same. As the aliases contain spaces, they have been
enclosed within double quotes.

So, giving column aliases has made the calculated column more descriptive.
Arithmetic operations follow some rules of precedence.



Rules of Precedence
If there is more than one operator used in an arithmetic expression, then operator
precedence comes into picture. In operator precedence, multiplication and division


© SQL Star International Ltd.                                                          67
take precedence over addition and subtraction. If operators having the same priority
are there within an expression, then they are evaluated from left to right.
Suppose, the New Jersey Central Library wants to increase its total earnings by way
of membership fee. Assuming that at least 10 persons belonging to each grade enroll
as members of the library every year, the proposed earnings would be as follows:

       SELECT cGrade grade, nFeeAmount+20 “Revised fee/member”,
       10*12*nFeeAmount+20 “Proposed Earnings”

       FROM MemberFee;

On the issue of the above query, the following result is displayed:




The above statement displays three columns: Grade, Revised fee/member and
Proposed Earnings. This SELECT statement calculates the revised fee to be paid by
each member (nFeeAmount+20) and the proposed earnings for the entire year
assuming each grade has 10 new members enrolled (10*12*nFeeAmount+20). You
will notice that in the expression 10*12*nFeeAmount+20, multiplication is performed
before addition. Since, there are two multiplication operations, they are performed
from left to right.
In order to override the rules of precedence, you can use parentheses. The
expression within the parenthesis would be evaluated first. We shall override the
precedence in the above statement using parentheses as follows:

       SELECT cGrade, nFeeAmount+20 “Revised fee/member”,
       10*12*(nFeeAmount+20)“Proposed Earnings”
       FROM MemberFee;

On the issue of the above query, the following result is displayed:




In the above SELECT statement, parentheses have been used to cite the order in
which the operations are to be performed. The SELECT statement calculates the
proposed yearly income by incrementing the fee amount by 20 and then multiplying
the result by 12 (12 months) and 10 (assuming 10 members enroll in each grade).



© SQL Star International Ltd.                                                    68
While using arithmetic operations there are certain aspects you must be aware of.
For instance, the role DUAL table plays, in performing arithmetic operations and the
result of an arithmetic operation that involves a null value.



Role of the DUAL Table

Until now the arithmetic calculations you have performed were all based on numeric
values extracted from database tables. But you may not always want to perform
calculations on data from a table. For instance, you may want to perform some
calculations on values not part of any table. In such a case, the Oracle server does
not have any real table to extract data from. But, it is mandatory to specify column
names after the SELECT keyword and a table name after the FROM keyword (that is,
every SELECT statement must have a FROM clause). Therefore, why not extract data
from a dummy table? The Oracle server provides a table called DUAL which will serve
the purpose of satisfying the FROM clause. The DUAL table does not have any
meaningful data. It contains one column called DUMMY with one row having a value
‗X‘.

For example, the DUAL table is used to perform arithmetic calculations on constant
values as shown below.

       SELECT 6788+2292
       FROM DUAL;




NULL Values and Arithmetic Operations

If a particular column of a row does not have value, that value is called null. It is not
the same as zero or a space, for zero is a number and a space is a character.


Care needs to be taken while performing arithmetic operations on columns that have
null values because they result in null.

For example, suppose the library intents to increase its earnings by way of
incrementing the fine charged to $2 from $1.5. To depict its future earnings the
following statement is written:

       SELECT nFine Fine, nFine +(1.5*0.25) ―proposed fine earnings‖
       FROM Transaction;

The query displays the following result:




© SQL Star International Ltd.                                                         69
The result shows some null values in the proposed fine earnings column. This is
because the nFine column values for some rows are null.

Using the Concatenation Operator

In addition to performing arithmetic calculations or changing column headings, you
can also join two or more columns to further refine (or change) the query result.

Concatenation is the method used to join two or more column outputs into one, to
produce more descriptive output. The resultant column is a character expression. It
is advisable to give an alias to the resulting column. The concatenation operator is (
|| ) two pipe characters put together.

You can join columns to

           Other columns

           Arithmetic expressions

        Constant values
For example, while retrieving details of members from the Member table, it would be
more appropriate to join the cFirstName and the cLastName columns to produce a
single member name column.

       SELECT cFirstName||cLastName AS NAME
       FROM Member;

On the issue of the above statement, the following result is displayed:




      ---------------------------

© SQL Star International Ltd.                                                      70
21 rows selected.

The above SELECT statement has joined the first name and the last names of
members using the concatenation operator.

What are Literal Character Strings?
A literal character string refers to any character, number or date included in the
SELECT statement, but which is neither a column name nor a column alias. They are
printed for each row returned by the query.
Date and character literals need to be enclosed within single quotation marks (‗ ‘) but
not number literals. For example, while retrieving the distinct book names along with
their respective authors from the Book table, concatenate the two columns with a
literal to make each row returned by the query more meaningful.

       SELECT DISTINCT (cBookName ||‘written by ‗
       ||cAuthorName) AS ―Book Details‖
       FROM Book;

On the issue of the above statement, the following result is displayed:




        49 rows selected.




Alternative Quote (q) Operator

The usage of character literals becomes obvious in many SQL SELECT statements or
select expressions. Use an (q) operator if the literal itself contains a single quotation
mark. This operator allows the developer to choose customized quotation mark
delimiter.

You can choose from a variety of delimiters, single-byte or multi-byte, or one of the
following character pairs: [ ], { }, ( ), or < >.

The following example will further explain the use of this operator:

SELECT department_name || q‘[, it‘s assigned Manager Id: ]‘ || manager_id
AS ―Dept and Mgr‖

FROM Departments;


© SQL Star International Ltd.                                                         71
In the example shown, the string contains a quotation mark, which is interpreted as
a delimiter. Using the q operator, the brackets [] are used as the quotation mark
delimiter. The string between the brackets delimiters is interpreted as a literal
character string.

Using Script Files



The statements entered in the Enter Statements field of iSQL*Plus can be saved to
text files (known as script files) as follows:

       1. Enter the SQL statement in the Enter Statements field, and click the Save
          Script button.




       2.   Select Save this file to disk radio button from the file download dialog
            box. Specify a file name and save it as shown below.




© SQL Star International Ltd.                                                    72
To use the saved script:

       1. Type the script name and location in the File field as shown below or click
          the Browse button to find the script file name and location.




       2. Click the Load Script button to load the file contents into the Enter
          Statements field of iSQL*Plus.


© SQL Star International Ltd.                                                      73
3. Click the Execute button to run the file contents.


DESCRIBE Command: It is an iSQL*PLUS command used to display the structure of
a table.
The syntax for the DESCRIBE command is

       DESCRIBE tablename

Let us look into the following example and the output it generates, to discuss this in
details.

       DESCRIBE Member




The Describe command gives us the information about:
COLUMN NAME       -      Name of the columns in the order it was created.
NULL              -      Where the column can hold null value or not.
DATATYPE          -      Column data could be of any of the following types:

Character type

Character datatypes represent all letters, numbers and special characters on the
keyboard.

Following are some of the character datatypes:

VARCHAR2 holds a character data of variable length with a default minimum size 1
and maximum size 4000.



© SQL Star International Ltd.                                                      74
CHAR holds a character data of fixed length with a default minimum size 1 and
maximum size 2000.

LONG holds Character data of variable length up to 2 gigabytes.
For example, names of members in the Member table are of CHARACTER datatype.

Number type

The datatype used to store only numeric data is the number datatype, NUMBER
(precision, scale). It can store both fixed and floating-point numbers. By precision we
mean the total number of digits and scale is the number of digits to the right of the
decimal point. For example, 779.69 is number datatype where the precision is 5 and
the scale is 2.
In the Member table, member‘s age is stored as NUMBER datatype.

Datetype

In Oracle, date data are stored in the DATE datatype, which actually contains two
values: the date, and the time between January 1, 4712 BC and December 31, 9999
AD. The default date format in which Oracle stores date is DD-MON-YY where DD is
the day of the month (01), MON is the month (Jan) and YY is the year (two-digit
year-99).




Summary

In this chapter, you have learnt that:


       To retrieve data from the database, a SELECT statement is used.

       SQL statements can be executed in either SQL*Plus environment or iSQL
           Plus environment where, iSQL Plus is a browser environment introduced
           in Oracle9i.

       SQL statements can be categorized into:
            SELECT statement- to extract data
            Data Definition Language- To create data

© SQL Star International Ltd.                                                       75
Data Manipulation Language- To modify data
              Transaction Control Language- To manage transactions done using DML
              Data Control Language- To control data access

      You can either select all columns of a table (using SELECT *) or select
        only specific columns of a table (using the column names) .

      To eliminate redundant data from the output, DISTINCT keyword is used.



      Column names can be given aliases to make them meaningful.

      DUAL is a dummy table used for arithmetic calculations.

      Use of operators like Concatenation helps to refine the retrieved data.




Lab Exercise
1.     Begin an iSQL*Plus session using the username and password provided to
you by       your instructor.

2.    Display the structure of the Departments table. Select all the rows from the
      Departments table.

3.    Display the structure of the Employees table. Write a query to retrieve the
      employee ID, first name, last name, job ID, hire date, department ID, and
      salary from the Employees table. Save the query to script file. Name the file
      as            LabEx03_03.sql.

4.    Look at the following SELECT statement. Can you identify any coding errors?
      SELECT Employee_ID, First_Name, Job_ID
      Salary x 0.1 Raised Salary
      FROM Employees;
      Execute the above statement and observe the error messages displayed.

5.    Write a query to display the unique department numbers and job IDs from
      the Employees table.




© SQL Star International Ltd.                                                        76
6.    Write a query to display the last name, job ID, salary and annual
      compensation of each employee. The annual compensation is to be calculated
      by adding a bonus of $500 to monthly salary, and then multiplying the result
      by 12. The query should combine the last name and job ID to make a single
      column named as ‗Employees‘. Give an alias ‗Annual Compensation‘ for the
      calculated column. The query should display the result as follows:




7.    Copy the contents of LabEx03_03.sql file into the iSQL*Plus Edit window and
      make the following modifications:

         Name the Employee_ID column as ‗Emp_No‘

         Concatenate first name and last name of employees separated by a space.
           Name the column as ‗Emp_Name‘

         Name Department_ID column as ‗Dept_No‘
           The query should display the result as shown below.




8.    Write a query to display the following output:




© SQL Star International Ltd.                                                   77
9.     Write a query to display the following text using q operator.


             Oracle’s quote operator




© SQL Star International Ltd.                                             78
Chapter 4




                                Enhancing Data Retrieval

                                   Restricting Data Using WHERE Clause
                                             Using Comparison Operators
                                         Working With Logical Operators
                                                           Sorting Data




© SQL Star International Ltd.                                      79
Objectives


At the end of this chapter, you will be able to:

Use     WHERE clause in the SELECT statement

   Work with comparison operators

   Work with Logical operators

Use     ORDER BY Clause




© SQL Star International Ltd.                       80
Enhancing Data Retrieval
A simple SELECT statement retrieves data for all the rows in a table. The rows
retrieved are not in any specific order. You can restrict the rows to be retrieved and
also specify the order of retrieval.
There are two clauses available to accomplish these tasks. They are the WHERE clause
and the ORDER BY clause.

Restricting Retrieved Data

You can retrieve only some rows from a table instead of all the rows depending on the
requirement. For example, imagine how tedious it will be if you have to find out those
members who have issued a particular book from a table containing data about
hundreds and thousands of members. But this task could be simplified by singling out
those rows that don‘t meet your criteria. This can be achieved by using the WHERE
clause. Its syntax is:

       SELECT [DISTINCT] {* | column [alias]…}
       FROM table
       [WHERE condition(s)];

The WHERE clause comes after the FROM clause and it contains a condition, which
may or may not be met.
The WHERE clause condition is made up of three elements:

          The column name

          Comparison operators

       The column values
Rules for using the column values in the WHERE clause :

          Enclose all character and date values within single quotation marks.

          Column values (character values in particular) are case sensitive but
            column names are not. Therefore, ensure that in the WHERE clause the
            character values are entered in their right case (uppercase, lowercase or
            mixed case).

          Date values are format sensitive. The Oracle server stores date in
            the default format, which is DD-MON-YY. Therefore, ensure that in
            the WHERE clause the date values are entered in this default format.

Comparison Operators

As the name suggests, comparison operators are used in the WHERE condition to
compare one expression to another. Following are the comparison operators used:




© SQL Star International Ltd.                                                       81
Using Comparison Operators

Based on a query made by a member to display all the books written by ‗Enid Blyton‘,
the following SELECT statement is issued:
        SELECT DISTINCT (cBookName)
        FROM Book
        WHERE cAuthorName = ‗Enid Blyton‘;
The result of the query is:




To illustrate the usage of other operators look at the example given below.
For the purpose of preparing a report, which shows the IDs of all those members, who
are above the age of 21, the following SELECT statement is issued:

       SELECT cMemberID
       FROM Member
       WHERE nAge >21;

The result of the above query is:




© SQL Star International Ltd.                                                  82
Similarly you can use >=, <, <= and <> operators in the WHERE clause.
Along with these operators there are other comparison operators such as,

          The BETWEEN operator

          The IN operator

          The LIKE operator

          The IS NULL operator




BETWEEN Operator

Using the BETWEEN operator, you can extract rows which fall within the range of
values specified. The operator comprises of a lower range and an upper range. The
lower range must be specified first. Both the values specified in the operators are
inclusive.
For example, the following statement is written in order to satisfy a member‘s query
regarding details of all those books published between 1965 and 1980:

       SELECT DISTINCT (cBookName)
       FROM Book
       WHERE dPublishedYr BETWEEN ‘01-JAN-1965' AND ‘31-DEC-1980';




IN Operator

When you use the equal to (=) operator, you are equating an expression with a value.
Whereas, in case of the BETWEEN...AND…operator a range of values is specified. But,
if you need to compare an expression to a list of values (may be the first, third, tenth
and sixteenth values), then you need to use the IN operator. The IN operator specifies
a list of values, which could be of any datatype.

© SQL Star International Ltd.                                                      83
For example, to retrieve details of those books written by ‗Shakespeare‘, ‗Nora
Roberts‘, and ‗Mary Higgins Clark‘, issuing the following SELECT statement would
result in an error:

       SELECT DISTINCT(cBookName)
       FROM Book
       WHERE cAuthorName = ‗Shakespeare‘,
       ‗Nora Roberts‘, ‗Mary Higgins Clark‘;

Following is the error message displayed when the statement is executed:
       *
       ERROR at line 3:
       ORA-00933: SQL command not properly ended

The SELECT statement resulted in an error because the ‗=‘ operator is used only to
equate one value. Hence, rewrite the statement using the IN operator.

       SELECT DISTINCT(cBookName)
       FROM Book
       WHERE cAuthorName IN(‗Shakespeare‘, ‗Nora Roberts‘, ‗Mary Higgins
       Clark‘);

The result of the query is:




LIKE operator

You may not always remember the exact value you are looking for in the database
tables. To overcome this problem, Oracle has provided the LIKE operator wherein you
can retrieve those rows that match the character pattern specified in the operator. The
method of matching expressions to a character pattern is called a wildcard search.
Following are the symbols used to create a character pattern:
% :- Sequence of zero or more characters preceding the character specified before the
symbol. Example,
To extract member names starting with A, use LIKE ‗A%‘ in the WHERE clause.
_ :- Any single character preceding the character specified before the symbol.
For example, to extract those member details who have the second letter in their
names as alphabet ‗a‘, use LIKE ‗_a%‘ in the WHERE clause.

       SELECT cFirstName||cLastName ―Member Name‖
       FROM Member
       WHERE cFirstName LIKE ‗_a%‘;

© SQL Star International Ltd.                                                     84
The query gives the following result:




But suppose you need to have an exact match for the actual symbols ‗%‘ and ‗_‘, and
then you need to use the ESCAPE option. In this option you need to specify what the
ESCAPE character would be.
For example, suppose one of the branch names of the library that needs to be queried
is ‗Dover_Brnc‘, then your ESCAPE option would be as follows:

       SELECT cBranchID, cBranchName, cBranchLocation
       FROM Branch
       WHERE cBranchName LIKE ‘%_%’ ESCAPE ‘’;

And the result set would be:
      CBRANCH        CBRANCHNAME          CBRANCHLOCATION
      -------        -----------          ---------------
      06DOVNJ        Dover_Brnc           Dover

In this SELECT statement the ESCAPE option specifies the escape character to be
backslash (). Since the escape character precedes underscore (_), it causes the
Oracle server to interpret the ‗_‘ literally causing the statement to retrieve details of
branch ‗Dover_Brnc‘.




IS NULL Operator

Since a NULL value stands for anything that is unavailable or unknown, you cannot use
the (=) operation because null cannot be equal or unequal to any value. So, you have
the    IS NULL operator to test for null values.
For example, the library resolves to bestow certain facilities such as extending the due
dates of all those members who are punctual in returning books. To identify these
members the following SELECT statement is issued:

      SELECT cMemberID FROM Transaction
      WHERE nFine IS NULL;
Which displays:

© SQL Star International Ltd.                                                       85
12 rows selected.
The statement retrieves those members who have not paid any fine amount.




Logical Operators

So far in the WHERE clause you have used only one condition. But, with logical
operators you combine conditions. Two or more conditions are joined together to
produce a single output by using the following logical operators:

         AND

         OR

         NOT




AND Operator



© SQL Star International Ltd.                                              86
If the desired rows are to be selected, then both the conditions specified in the WHERE
clause must necessarily evaluate to TRUE.
For example, to retrieve only those books that are stored in branch ‗04RANNJ‘ and
which were published in the years ranging from 1965 to 1980, a SELECT statement
using the AND operator needs to be written as shown below.

       SELECT cBookName
       FROM Book
       WHERE dPublishedYr BETWEEN ‘01-JAN-1965' AND ‘31-DEC-1980'
       AND cBranchID = ‘04RANNJ‘;

The query displays the following result:




If a member has not paid fine, it does not necessarily mean that he has returned the
borrowed books on the due dates. This is because the nFine column of a member
whose due date is yet to come will also be null. Hence, to find out those members who
have not defaulted, the following SELECT statement using the NOT operator is to be
written as shown below.

       SELECT cMemberID
       FROM Transaction
       WHERE nFine IS NULL
       AND dActualReturnDt IS NOT NULL;

The result of the query is:




                   9 rows selected.
By using two conditions in the WHERE clause, the above statement returns those
members who have returned the borrowed books on their due dates. The two
conditions are:

          To retrieve the IDs of those members who have not paid any fine

            and
© SQL Star International Ltd.                                                     87
   To retrieve the IDs of those members who have returned the borrowed
            books.


The above statement uses the logical operator NOT in the WHERE clause as follows:
AND dActualReturnDt IS NOT NULL
The NOT operator specifies that the date on which the member returned his books is
not null (that is, he has returned the books).
The result of joining two expressions using the AND operator is given using the AND
TRUTH table.




OR Operator

In order to select the desired rows, either of the conditions specified in the WHERE
clause can be TRUE.
For example, to retrieve books written either by ‗Nora Roberts‘ or those that belong to
the ‗mystery‘ category, the following statement is issued:

       SELECT DISTINCT(cBookName)
       FROM Book
       WHERE cAuthorName = ‗Nora Roberts‘
       OR cCategoryID = ‘01MYS‘;

The result of the query is as follows:




The result of joining two expressions using the OR operator is given below using the
OR TRUTH table.




© SQL Star International Ltd.                                                     88
NOT Operator

Operators such as BETWEEN, IN, LIKE and NULL can be used along with the NOT
operator. You have already seen its usage in one of the examples above. Here is
another one.
For example, the library database user issues the following statement in order to
display those books not written by ‗Robert Louis Stevenson‘ and ‗Michael Crichton‘:

       SELECT DISTINCT(cBookName)
       FROM Book
       WHERE cAuthorName NOT IN (‗Robert Louis Stevenson‘, ‗Michael Crichton‘);

The result of using the NOT operator in a condition is given in the NOT TRUTH table.




Order of Evaluation

The order in which the operators are evaluated are:




/This order of evaluation can be overridden using parentheses.
An example illustrating the rules of precedence:

       SELECT cBookName
       FROM Book
       WHERE cBranchID =‘01ADLNJ‘
       AND cAuthorName = ‗Charles Dickens‘
       OR nNoOfCopies = 2;
© SQL Star International Ltd.                                                     89
The query result is as follows:




          ----------------------------
          24 rows selected
In this example there are two conditions:

          The first condition mentions that branch ID must be 01ADLNJ and author
            must be ‗Charles Dickens‘.

        The second condition mentions that the quantity of books stored must be 2.
But, to retrieve those books written by ‗Charles Dickens‘ and stored in branch
‗01ADLNJ‘ or those books whose quantity stocked is 2,the above example could be re-
written as below:
As per the rule of precedence, the AND condition has a priority over the OR condition.
You can override this by using parenthesis as shown in the following statement:

       SELECT cBookName
       FROM Book
       WHERE cBranchID = ‘01ADLNJ‘
       AND (cAuthorName = ‗Charles Dickens‘
       OR nNoOfCopies = 2);

Which gives the result:




Now, the two conditions in this example are:

          The author must be ‗Charles Dickens‘ or the number of copies must be 2.

          The branch ID must be ‗01ADLNJ‘.



© SQL Star International Ltd.                                                     90
Sorting Retrieved Data

Data stored in the tables do not follow a particular sequence. They are neither sorted
in the ascending nor descending order of precedence.


You can use the ORDER BY clause to fetch rows in a specific order. The ORDER BY
clause is the last clause in the SELECT statement.
The syntax for using the ORDER BY clause is:

         SELECT <column_name>…
         FROM <table_name
         [WHERE condition(s)]
         [ORDER BY {column, expr} [ASC | DESC] ];

Where,

ORDER BY clause is used to sort the rows to be fetched.
ASC specifies that the rows are to be sorted in the ascending order, which happens to
be the default order.
DESC specifies that the rows are to be sorted in the descending order.
When you issue a SELECT statement to retrieve member details from the Member
table, the resulting rows are not in any sequential order.

         SELECT cMemberID, nAge
         FROM Member;
         The query gives the following result:




               ------------------
               21 rows selected.
But if you want to retrieve member details sorted according to their ages, issue the
following SELECT statement:

         SELECT cMemberID, nAge
         FROM Member
         ORDER BY nAge;

The query gives the following result:




© SQL Star International Ltd.                                                    91
------------------
            21 rows selected.
This statement displays all the members sorted according to their ages. The rows are
sorted in ascending order, as it is the default way of sorting.
The ascending order of sorting for different datatypes is as follows:

         Number data values are fetched with the lowest values first.

         Character data values are fetched in the alphabetical order from A to Z.

         Date data values are fetched with the earliest date first. For example,

           17-OCT-97 will be displayed before 17-OCT-99.

         Null values are fetched last.
In order to reverse the default sorting order, you need to specify the DESC keyword
after the column name in the ORDER BY clause.
The above statement had retrieved details from the Member table beginning from the
junior most (age wise) members. To retrieve the details of the senior members, issue
the following statement:

       SELECT cMemberID, nAge
       FROM Member
    ORDER BY nAge DESC;
The result of the query is:




              -----------------------------
               21 rows selected.
In case an alias has been assigned to the column based on which you intend to sort
the result, then you can use the column alias in the ORDER BY clause.

      SELECT cMemberID,nAge,dMembershipDt ―Membership Date‖ FROM Member
      ORDER BY ―Membership Date‖;

© SQL Star International Ltd.                                                         92
The result of the query is as follows:




         ------------------------
         21 rows selected.
In the ORDER BY clause, you can specify more than one column each separated using
commas.
For example, to display the names of the library members sorted according to their
membership dates and age, the following statement is issued:

       SELECT cMemberID, cFirstName, cLastName
       FROM Member
       ORDER BY dMembershipDt, nAge DESC;

The result of the query is:




              --------------
               21 rows selected.
This statement orders the result by membership date and then by descending order of
members‘ age.
One interesting aspect that comes out of this example is that you can sort by columns
not specified in the SELECT clause. Neither dMembershipDt nor nAge columns based
on which the result has been sorted have been specified in the SELECT clause.




© SQL Star International Ltd.                                                   93
Summary

In this chapter, you have learnt that:

         Use of WHERE clause in a SELECT statement lets you to retrieve only the
        required data and ORDER BY clause arranges the retrieved data in a specific
        order.
        
         Comparison operators such as BETWEEN..AND, LIKE, IN, IS NULL along with
        relational operators (>, <, <=, >= etc) and logical operators (AND,OR,NOT)
        can be used in the WHERE clause condition to restrict the output.

         ORDER BY clause sorts the data either in ascending or descending order
        using
         keywords ASC and DESC respectively.
        
         Column specified in the ORDER BY clause need not be mentioned in the
        SELECT clause of the query.


Lab Exercise
1. Write a query to display details of employees whose job ID is ‗ST_CLERK‘.
2. Write a query to display last name, job ID, department number and salary of
   employees whose salary is greater than $14,000.
3. Write a query to display last name, department number and hire date of employees
   hired between 01-JAN-1995 and 31-DEC-1999. Sort the query in descending order
   of hire date.
4. Write a query to display the employee ID, first name and manager ID of employees
   whose manager ID is 100, 108, 148 or 120.
5. Write a query to retrieve the last name and hire date of employees hired in 1997.
6.   Write a query to retrieve the employee ID, last name and job ID of employees
     whose job ID contains the string ‗SH_‘.
7. Write a query to retrieve the first name, job ID and Department number of
   employees who do not have a manager.
8. Write a query to retrieve the employee ID, last name, salary and commission of all
   employees who earn a commission. Sort the query result in descending order of
   salary.
9. Write a query to retrieve the last name, department number, job ID and salary of
   employees if, the job ID is ‗SA_MAN‘ or ‗SA_REP‘, and if the employee earns a
   salary more than $10,000. The query result should be as shown below:




© SQL Star International Ltd.                                                      94
8 rows selected.

10.   Write a query to retrieve the last name, job ID, department number and salary
for employees whose department ID is 50 or whose job ID contains the string ‗MAN‘.
The query result should be as shown below:




11.    Write a query to display the details of employee whose last name is ‗ernst‘.




© SQL Star International Ltd.                                                         95
Chapter 5




        Generating Formatted Reports using iSQL*PLUS
                                         Substitution Variables
                                   Using Pre-Defined Variables
                                  Producing Formatted Reports
                                     Using FORMAT Commands
                                Creating Formatted Script Files




© SQL Star International Ltd.                               96
Objectives


  At the end of this chapter, you will be able to:

    Write queries requiring user input

    Format the output using the various iSQL*PLUS commands

    Create script files to run reports




© SQL Star International Ltd.                                  97
iSQL*Plus Substitution Variables
SQL comprises of statements that are entered into the command line. On
encountering an SQL statement, the Oracle server‘s SQL processing mechanism
returns the required data. After returning the data, it is ready to execute the next
statement that is entered.

For example, in order to retrieve the address details of a member with ID
‗DDG019503‘, you must issue the following SELECT statement:


       SELECT cFirstName||cLastName Name, vAddress, cArea
       FROM Member
       WHERE cMemberID = ‗DDG019503‘;


On encountering this statement, the Oracle server returns the data that corresponds
to the cMemberID value specified in the WHERE clause.




On running the above query again, the Oracle server returns the same data because
its range is predetermined by the fixed WHERE clause of the query. This query will
not hold good if the librarian wants to retrieve address details of any other member.
Therefore, the query issued is not interactive. It could be made interactive by
enabling the librarian to enter values that determine the range of data to be
returned, at runtime. Oracle server‘s SQL processing mechanism contains features
that enable users to specify their own values to restrict the range of data to be
retrieved at runtime. This is achieved by using iSQL*Plus substitution variables (also
known as runtime variables).

Substitution Variables

Several times when developers execute a query, they do not know what value the
user may want to use to restrict the range of data to be returned. Therefore, they
hard code the value into the statement. However, it is cumbersome when the same
query is issued each time with a different value to restrict the range of data to be
retrieved.

For instance, when the librarian extracts the address details of a member with ID as
‗DDG019503‘, the cMemberID column value is hard coded in the WHERE clause.
However, if he uses the same statement to extract address details of a member with
ID as ‗DCF058502‘, he would be unable to do so.

To make the statement reusable and flexible, substitute the hard-coded member ID
value with a variable that prompts the user to enter different member ID values each
time the statement is executed. These variables are known as substitution variables.


© SQL Star International Ltd.                                                          98
In iSQL*Plus environment, single-ampersand (&) substitution variables are used to
store temporary values.
The statement used to retrieve data from the Member table based on the hard-
coded member ID value can be rewritten by using the substitution variable (&) as
follows:
      SELECT cFirstName||cLastName Name, vAddress, cArea
      FROM Member
      WHERE cMemberID=‘&MemID‘;


In the statement, the MemID variable is prefixed with a single ampersand (&). Doing
so, informs the Oracle server that the user should be prompted for a member ID
value each time the statement is executed.




                    The output is:




On entering the member ID value, the query displays the name and address for that
member.
© SQL Star International Ltd.                                                   99
Now the SQL statement is a flexible statement, therefore, you can re-execute it by
specifying a different member ID value at run-time.

You can verify the changes made on re-executing the statement by using the SET
VERIFY command. Setting SET VERIFY ON displays the value before and after it is
replaced by the substitution variable. Before a variable is replaced by the user-
provided value, the old value is always the variable itself.
Points to remember while using substitution variables:

    Enclose substitution variables within single quotes if they are used to store
character or date values. If they are used to store number datatypes, single quotes
are not required.

   For example, … WHERE cMemberID = ‘&MemID’;


     Functions such as UPPER and LOWER can be used with substitution variables.
For example, using UPPER(‗&BkName‘) indicates that the user need not enter the
book name in uppercase.

      You can use substitution variables not only in the WHERE clause but also in
the following clauses:

                         The ORDER BY clause
                         Column names in the SELECT clause
                         Table name in the FROM clause

Use substitution variables in the ORDER BY clause when you want to sort the result
of a query on the Book table according to a column of your choice.


       SELECT cBookID,cBookName,&ColumnName
       FROM Book
       WHERE &Condition
       ORDER BY &SortingColumn;

On executing the statement, the book ID, book name and any other column that the
user specifies at runtime into the ColumnName substitution variable, is displayed.
These columns are retrieved by the condition the user specifies into the Condition
substitution variable for their retrieval and the column by which the retrieved data is
to be sorted.




© SQL Star International Ltd.                                                      100
© SQL Star International Ltd.   101
The output is:




Many times a user may want to use the same variable value more than once without
being prompted for a value each time.




© SQL Star International Ltd.                                               102
For example, the librarian may want to retrieve book details sorted by the same
column he specifies for the substitution variable. But by using single-ampersand
substitution variable, each time he re-executes the statement, he would be
prompted for the column value with which the data is to be sorted. In order to be
prompted for a value only once, the double ampersand (&&) substitution variable is
used in the following manner:


       SELECT cBookID,cBookName,&ColName
       FROM Book
       ORDER BY &&Column;


Re-executing the above statement retrieves book Ids, book names and any other
column that the librarian specifies to be placed in the single ampersand ColName
substitution variable. But each time, the retrieved columns are sorted according to
the same column he specifies in the double ampersand Column substitution variable.
Yet, entering new values for single ampersand variables or using the same value that
is placed into the double ampersand variable may not always be useful. For example,
the values entered into the ColName can be used only in the statement in which they
have been defined. Once the variable value is used, iSQL*PLUS discards it, thereby,
requiring you to enter a new value each time. Instead of running the statement over
and over again so as to enter new values, you could predefine variables with values
before executing the statements. This is done by using two iSQL*PLUS commands:
DEFINE and ACCEPT.


Predefining variables

The two iSQL*Plus commands used to predefine variables are:
                     DEFINE
                     ACCEPT

The DEFINE Command

Values for runtime variables are defined by using the DEFINE command. The
command defines the input value of a variable before executing any statement.
Therefore, unlike substitution variables, any statement can use them, as the value is
not discarded once it is used in that session.
In case the library desk officer wants to make queries about information on books
from the Book table and from the Transaction table, she may do so by using a
substitution variable for accepting the ID of the book.
       SELECT cBookName Books
       FROM BOOK
       WHERE cBookID=‘&BookID‘;




© SQL Star International Ltd.                                                    103
The output is:




The disadvantage of this query is that other SELECT statements cannot use the
substitution variable used in the above SELECT statement.
Therefore, the DEFINE command can be used to avoid entering values for variables
each time the statements are run. It assigns a value to a CHAR datatype variable
that gets created.
The DEFINE command is issued with the following syntax:

      DEFINE <variable_name> = value

To enhance the above statement, issue the DEFINE command in the Enter Statement
field and click the Execute button.

      DEFINE BookID = ‗MYS040000068‘

To display the values in a variable, use the command with the variable name as
shown.
      DEFINE <variable_name>
      DEFINE BookID

The above command displays the following result:

      DEFINE BOOKID = ―MYS040000068‖ (CHAR)

The value you have defined into the BookID variable can now be used in any of the
statements as follows:


© SQL Star International Ltd.                                                    104
SELECT cBookName FROM Book
       WHERE cBookID=‘&BookID‘;




Or you can issue

       SELECT cTranID,dIssueDt
       FROM Transaction
       WHERE cBookID=‘&BookID‘;

The output is:




The variables defined with this command remain throughout the session unless you
undefine them. By un-defining the variables, they can be reused. To undefine the
BookID, give the following command.
       UNDEFINE BookID
You can confirm the change made, by issuing the DEFINE command.

       DEFINE BookID
Displays:
       SP2-0135: symbol bookid is UNDEFINED




                    ACCEPT Command:

                    ACCEPT command requests value for a variable from the end
                    user.

                    Syntax:

                           ACCEPT <variable_name> datatype

                    Example: ACCEPT vage NUMBER


© SQL Star International Ltd.                                               105
SELECT * FROM Member WHERE nage=&vage;

                     A variable declared using a DEFINE command is always of
                     character datatype, whereas you can specify the datatype for a
                     particular variable using ACCEPT command.


                     Producing Formatted Reports
When users execute queries they are presented the data, as it is stored in the tables.
But reports need to be formatted so as to be more presentable and expressive. This
is made possible by using:


                      SET commands
                      FORMAT commands

Using SET Commands

                     SET commands are used to control the session environment in
                     which iSQL*Plus operates. Following is the syntax to set the
                     session environment variables:

                            SET <system_variable> value

                     Where,
                     system_variable is a variable that controls the           session
                     environment.
                     value is the value of the session environment variable.

                     For example,

                            SET ECHO ON

                     This command sets the value of the session environment
                     variable ECHO to ‗ON‘.

                     Later, you can verify the values of all the session environment
                     variables that are set, using the SHOW command. For instance,
                     you can check the value of the ECHO variable in the following
                     manner:


                            SHOW ECHO
                     Displays:
                            echo ON


                     In order to verify all the system variables that have been set,
                     use the SHOW ALL command.

SET Command Variables




© SQL Star International Ltd.                                                     106
As mentioned earlier SET command variables are used to
                    control the environment of the current session. Following are
                    the SET command variables:




                    In the commands, the underlined values are the default values.
                    n is a numeric value that the user enters. If no value is
                    entered, iSQL*Plus considers the default value.

                    For instance, set the system environment variable HEADING to
                    OFF in the following manner:

                           HEADING OFF

                    Now select the records from the Member table giving the
                    following query:


                           SELECT * FROM Member;
                    The output is:




© SQL Star International Ltd.                                                   107
Notice that the heading is not displayed in the output.
Using FORMAT Commands
                    The SET commands help only to control the current
                    environment settings. However, to format the report features
                    such as determining the way columns should be displayed, or
                    giving suitable headers and footers, use the FORMAT
                    commands.
                    The commands used to format reports are:

                     The COLUMN commands – to format column display
                     TTITLE and BTITLE commands– specify headers and footers
                       that should appear on each page of the report
                     BREAK command – suppresses duplicate values and helps
                       creating break reports

Using the COLUMN Commands
                    COLUMN commands control the way column data should be
                    displayed. This is done by using the following options with the
                    COLUMN command:




© SQL Star International Ltd.                                                    108
The syntax for changing the way column data is display is:

                             COL[UMN] [{column|alias}] [option]]

                    Where,

                    column|alias is the column whose data display is to be
                    formatted

                    option specifies the way the column data is to be formatted.

                    The following commands are used to show or to clear the
                    current column formatting:




                    The column command options discussed above are explained
                    here with the help of examples:

HEADING Option
                    This option sets the heading that appears for a particular
                    column.


                    For example, the heading of vAddress column could be
                    changed to make it more meaningful in the following way:


© SQL Star International Ltd.                                                      109
COLUMN vAddress HEADING ‗Member|Address‘

                     In the COLUMN command, the vertical line causes the word
                     after it to be placed on the next line. On issuing a SELECT
                     statement, you could see the result of the above setting.

      SELECT * FROM Member;

                     The output is:




                     -------------------

 21 rows selected.

The NULL Option
          The NULL option specifies the text to be displayed for null values. For
          example, while preparing a report to display all the member details, the
          library clerk may not want nfine column to show any null values.
          Therefore, he could replace it with text using the NULL option as follows:


                     COLUMN nFine NULL ‗No Dues‘

                     Issue the following SELECT statement in order to display the
                     text written using the NULL option:


                     SELECT cMemberID,nFine
                     FROM Transaction;


                     The following screenshot is the output: -




© SQL Star International Ltd.                                                     110
----------------

             32 rows selected.

                    Notice the nFine column with null values is populated with the
                    text ‗No Dues‘.

NOPRINT and PRINT Option
                    These options determine which columns are to be hidden or
                    shown while preparing reports.


                    For example, the librarian may not want the cGrade and nAge
                    columns to be displayed while selecting all the columns from
                    the Member table. To do so he could hide them by using the
                    NOPRINT option as follows:


      COLUMN cGrade NOPRINT
      COLUMN nAge NOPRINT


                    When you issue a SELECT statement specifying these two
                    columns, they will not be displayed.



      SELECT cMemberID, cGrade,nAge
      FROM Member;


                    Displays the following output:




© SQL Star International Ltd.                                                   111
--------------
    21 rows selected.

                     To display these columns, you can either clear the settings of
                     both the columns using the CLEAR option or use the PRINT
                     option as follows:


      COLUMN cGrade CLEAR
      COLUMN nAge PRINT


                     Having cleared the NOPRINT option, check the output of the
                     above SELECT statement. It displays all the columns specified
                     in the SELECT statement.


The FORMAT Option
                     The FORMAT option enables the user to change the display of
                     column data. There are different formatting models available to
                     change the display of number data and character data.

                     Number Formatting Model

Formatting            Description            Example        Result
 Character
               Specifies the display         FORMAT     2020-
               width of the number of        9999       acceptable
               digits to be entered. If                 152550- not
               there is a number                        acceptable. It
      9
               overflow, the Oracle                     returns
               Server displays ‗#‘. It                  1525##
               suppresses any leading
               zeros
               Enforces the display of       Format                  789
      0        leading zeros                 0999


               Places a dollar sign before    $99,999          $59,590
      $        the number




© SQL Star International Ltd.                                                     112
Displays local currency       L9999      Rs7878
      L         symbol before the number


                Specifies the position for      99,999            25,789
      ,         placing a thousand
                separator
                Specifies the position of a    9999.99          4562.75
      .         decimal point and rounds
                appropriate




                      Examples of some formatting models are:


      Column nFeeAmount FORMAT $999.99
      SELECT nFeeAmount
      FROM MemberFee;


                      Displays the following result:




Using the TTITLE and BTITLE Commands
          The TTITLE and BTITLE commands are used to format page headers and
          footers respectively. The syntax for both the commands is identical:


                              TTITLE|BTITLE [text| ON | OFF]

          Where,

          text represents what the page title or footer should be. Enclose the text in
          single quotes if it is more than a word.

          ON | OFF specifies whether the headers or footers are to appear on the
          report or not.

          For example, display a suitable header and footer for all the reports
          generated by the New Jersey Central Library.



© SQL Star International Ltd.                                                       113
TTITLE ‗New Jersey Central Library | Weekly Book Issue Report‘
        BTITLE ‗Confidential Report‘
      SELECT cTranID,cMemberID,cBookID,dIssueDt
      FROM Transaction;


                     The report displayed by the above statement is:




                       ------------------------

       31 rows selected.

        The TTITLE command displays ‗New Jersey Central Library‘ centered on the
        first title line and ‗Weekly Book Issue Report‘ centered below it. The TTITLE
        command automatically displays the date and page number on every page
        in the report.

        The BTITLE command displays ‗Confidential Report‘ centered below every
        page of the report. You can use the words RIGHT and LEFT with BTITLE to
        right or left justify the text other than the center of the page.

        An enhancement over             TTITLE    and   BTITLE   is   the   REPHEADER   and
        REPFOOTER commands.

        You have seen the default behavior of the TTITLE command. This is
        sufficient for most of your report generating activities. But, some reports
© SQL Star International Ltd.                                                           114
would require more sophistication         such as placing the clerk‘s name
        (who is preparing the report), or place page numbers at the specified
        position, etc. This is met by using the REPHEADER command.

        The REPHEADER command places a specified title at the top of each report
        and formats it. Its syntax is,

             REPH [EADER] [PAGE] [printspec [text| variable]...]|[OFF|ON]

        The syntax is the same even for REPFOOTER.

        Where,
        PAGE starts a new page after printing the specified report header or before
        printing the specified report footer.

        printspec represents one or more of the following clauses used to place the
        text and format it:

                  COL n - Indents to position n of the current line
                  S[KIP] [n] – determines the number of lines to be skipped. If
                       you omit n, one line is skipped at a time; if you enter zero
                       for n, the print position goes backward to the start of the
                       current line.
                  TAB n - Skips forward n print position. If you enter a negative
                       value for n, it skips backward.
                  LE[FT] CE[NTER] R[IGHT] – specifies how the text is to be
                       justified.
                  BOLD - Prints data in bold print.
                  FORMAT text - Specifies a format model that determines the
                       format of the data items. Refer to the FORMAT clause of the
                       COLUMN command in this chapter
                  Text - Represents the report header or footer text. Enter text in
                       single quotes if you want to place more than one word on a
                       single line.
                  OFF - Turns the report header or footer off (suppresses its
                       display) without changing its definition.
                  Variable – represents any of the following system generated
                       variables like:
                         Sql.ino – specifies the current line number
                         Sql.pno – specifies the current page number
                         Sql.user – specifies the name of the user who has
                           logged in to iSQL*PLUS environment.



        If you do not enter a printspec clause before the text or variables,
        REPHEADER left justifies the text or variables.

        To understand these advanced clauses, let us use them to make a more
        sophisticated header and footer.
      REPHEADER LEFT ‗Report generated by Brad Riley‘-
      SKIP CENTER ‗New Jersey Central Library‘-
© SQL Star International Ltd.                                                    115
SKIP CENTER ‗Yearly Book Issue Report‘
      REPFOOTER CENTER ‗COFIDENTIAL -REPORT‘


                     Now run the query:


      SELECT *
      FROM Transaction
      WHERE dIssueDt BETWEEN ‘01-JAN-2000'          AND ‘31-DEC-2000';


                     It displays the following output:




 10 rows selected.




Using the BREAK Command
                     The BREAK command is used to suppress duplicate values.
                     To understand its usage, look at the result of the following
                     query without using the BREAK command:


© SQL Star International Ltd.                                                       116
SELECT cBranchID, cBookName, nNoOfCopies
      FROM Book
      ORDER BY cBranchID, cBookName;


                     The output of the statement is:




184 rows selected.

                     The query displays the books belonging to each branch. But
                     you will notice that the branches‘ IDs are repeated. In order to
                     suppress them, you should use the BREAK command. Its
                     syntax is:

                            BREAK ON column [ | alias ]

      BREAK ON cBranchID

                     After issuing the above BREAK command, observe the result
                     obtained by performing the following query:


      SELECT cBranchID, cBookName, nNoOfCopies
      FROM Book
      ORDER BY cBookName;




© SQL Star International Ltd.                                                     117
------------------

184 rows selected.




                 By issuing the BREAK command, the same query result changes. You
                 will notice that the branch ID ‗01ADLNJ‘ is printed only in line 1 and
                 is suppressed in lines 2 to 36, and from line 37 a different branch ID
                 is printed.




                 You will notice that the ordering of the query output by book name
                 hampers the suppression of duplicate branch IDs. This is because
                 you must always remember to order your query by the same column
                 on which you have issued the BREAK command.

                 But this report is quite incomplete without computing the total copies
                 of books that each branch stores. To do this, you need to just
                 mention what you want added up by using the COMPUTE command.

                 You will have to re-format the above query by incorporating the
                 COMPUTE command as follows:


       COMPUTE SUM OF nNoOfCopies ON cBranchID
       SELECT cBranchID, cBookName, nNoOfCopies
       FROM Book
       ORDER BY cBranchID, cBookName;

                      The output is:




© SQL Star International Ltd.                                                      118
------------------
184 rows selected.

                     The COMPUTE SUM OF nNoOfCopies ON cBranchID forces the
                     total number of copies for each branch to be printed only when
                     a new branch ID is printed.

                     Having used all the various commands to format your reports,
                     you need to remember some important points:

      All formatting commands remain in effect unless you end the current
iSQL*PLUS session or overwrite them.
      After every report, remember to reset the iSQL*PLUS settings to their default
values.
      There is no command available to reset the iSQL*PLUS settings to their
default values. You must either know the default value or log out and log in again.
      In case, you have assigned an alias for a column, then reference the alias
name instead of the column name.
      The entire standard SET commands, as well as, other iSQL*PLUS commands
required for every session are stored in a file known as the login.sql. As soon as you
CONNECT to a user in iSQL*PLUS environment, this file is read and all its commands
are implemented. These settings can be changed during the current session. But
they are in effect only for that session. Once you log out they are lost. Therefore, to
make them permanent add these settings to the login.sql file.




© SQL Star International Ltd.                                                      119
Creating Formatted Script Files
     All the iSQL*Plus commands you have covered so far could either be entered
     individually in the Enter Statement field or entered along with the SELECT
     statement into a script file (or command file). Creating a script file is
     recommended because all the formatting commands needed for the generation
     of a report could be kept in one place without having to enter them individually.
     You only need to run the script file for producing the result. You already know
     how to create script files. Now you will see further enhancements that can be
     made. However, before that you should understand the steps for creating script
     files.

Create a Script File for Formatted Results
The steps to be followed for creating script files are:
1. Issue a SELECT statement in the Enter Statement field and ensure
that before you save it to a file, the data it retrieves is accurate. Include the ORDER
BY clause if you intend to use the BREAK command.

 2. Edit the script file and enter the formatting commands before the SELE
statement. Ensure that you do not add them within the SELECT statement.

3. Add the format-clearing commands after the SELECT statement.


4. Save the changes made to the script file. In Oracle10g, you can have spaces in
the filename or within the directory path by enclosing them fully with double quotes.

Syntax to save a script in SQL*Plus:         SQL> SAVE ― <filename>‖

Example: SQL> SAVE ―d:training classes my script.sql‖

5. To execute the script file, click the Browse button, select the script file, and
click the Load Script button. Once the script is loaded, click the Execute button.

         To run the above script in SQL*Plus, give the following statement:
              SQL> @ ―d:training classesmy script.sql
 6. Use REM whenever you wish to add a remark or a comment in iSQL*Plus script
file.

Following the above steps, you can now create a script file to generate a report that
displays the total number of copies of books stored in each branch.

7. The required SELECT statement is entered in the iSQL*Plus Enter Statement field.




© SQL Star International Ltd.                                                       120
8. Save the statement to a script file called REPORT

                          9. Edit the REPORT script file to add all the formatting commands



      SET PAGESIZE 200
      SET LINESIZE 170
      SET FEEDBACK ON
      REPHEADER OFF
      REPFOOTER OFF
      TTITLE ‗NEW JERSEY CENTRAL LIBRARY‘
      BTITLE ‗CONFIDENTIAL REPORT‘
      BREAK ON cBranchName
      COMPUTE SUM OF nNoOfCopies ON cBranchName
      COLUMN cBranchName HEADING ‗Branch|Name‘
      COLUMN cBookName HEADING ‗Book|Name‘
      COLUMN cAuthorName HEADING ‗Author|Name‘
      COLUMN nNoOfCopies HEADING ‗Copies‘
      REM Insert a SELECT statement here


      SELECT B.cBranchName, Bk.cBookName, Bk.cAuthorName, Bk.nNoOfCopies

© SQL Star International Ltd.                                                                 121
FROM Branch B, Book Bk
      WHERE B.cBranchID = Bk.cBranchID
      ORDER BY B.cBranchName;


      REM clear all the settings
      SET FEEDBACK OFF


      CLEAR COLUMN
      TTITLE OFF
      BTITLE OFF
      CLEAR BREAK


      10.    Execute the script file and observe the result.


                     The report generated is more presentable as compared to the
                     result generated on executing a SELECT statement without any
                     formatting.




184 rows selected.
columns cleared
breaks cleared




© SQL Star International Ltd.                                                 122
SPOOL Command

                    In SQL*Plus, the output of a script can be directed to a file
                    using SPOOL command.

                    Syntax to use SPOOL command is :


      SQL> SPOOL <filename>
      SQL> SPOOL OFF



                    Example:


                           SQL> SPOOL d:test.txt
                           SQL> SELECT * FROM Member;
                           SQL> SPOOL OFF


                    The output of the above SELECT statement is stored in a text
                    file called test.
                    In Oracle10g, new option called APPEND has been added to
                    SPOOL command. It appends the output of a SPOOL command
                    to an existing file.
                    The above code can be re-written using APPEND command as


                           SQL> SPOOL d:test.text APPEND
                           SQL> SELECT * FROM Memberfee;
                           SQL> SPOOL OFF


                    In the test.txt file, the output of the above SPOOL command
                    gets appended.


                    SET SQLPROMPT
                    New variables have been introduced to set the prompt in your
                    SQL*Plus session with this release of 10g.

_DATE : the current date or a pre-defined string.
_PRIVILEGE : level of connection, SYSDBA, SYSOPER or NULL for normal.
_USER : user you are connected to.


Example


 SQL > SET SQLPROMPT ―_DATE : _USER‘@‘_CONNECT_IDENTIFIER _PRIVILEGE >
        ―
 20-MAY-04 : SYSTEM@prd9i >

© SQL Star International Ltd.                                                       123
If you want the column name in the condition to remain same each time you
     execute the query, use &&-double ampersand Substitution Variables.

   Variable can be pre-defined using DEFINE and ACCEPT command. DEFINE
     stores Character value by default. Datatype of a variable can be specified
     while using ACCEPT command.




Lab Exercise
1.    Display the Last Name, department and salary of the employees whose
employee id is 105.




                    Make the above query interactive.




© SQL Star International Ltd.                                                     124
After Execution:




             2.Write a query that prompts the user to specify the condition and the
             order by sorting column, using substitution variables.




© SQL Star International Ltd.                                                   125
6 rows selected.


3.Display employee details, by prompting the user to enter a column name he/she
wishes to view. The user should be prompted only once for the sorting column.




© SQL Star International Ltd.                                                 126
-------------------

                                108 rows selected.


            4.       For the report above, display the heading ‗Employees Report‘
            on the top of the page. (Give any name you like). Give a name for the
            person who generated the report. (You may use your own name.).
            Create a script file to generate employee Ids, first and last names,
            departments and job IDs and salaries of all employees sorted according
            to the department IDs. Format the report to include:

            a page size of 300
            line size of 100
            feedback off
            a title and subtitle for the report
            appropriate column headings
            word wrap
            format salaries to include decimals and thousand.
© SQL Star International Ltd.                                                  127
Once the script is run and the report generated, ensure that all the
            settings are back to the default.




© SQL Star International Ltd.                                                      128
Chapter 6




                                SQL Single RowFunctions

                                                  Types of SQL Functions
                                          Features of Single Row Function
                   Character functions - Case Manipulation and Character
                                                              Manipulation
                                             Number and DATE Functions
                                     Conversion- IMPLICIT and EXPLICIT
                                                          RR Date Format
                                                        General Functions
                                            Use of Conditional Expression




© SQL Star International Ltd.                                         129
Objectives

At the end of this chapter, you will be able to:

Use Character Manipulating Functions

Use Number Manipulating Functions

Use Date Manipulating Functions

Convert One datatype to another

Work with NULL values




© SQL Star International Ltd.                      130
Introduction
So far you have retrieved, restricted and sorted data from the database. But, the
real importance of the data lies in the way it is presented to the user. This requires
formatting the data. To format data values stored in the database, SQL provides
functions. Functions make your query more powerful.

Function Capabilities

Functions are an important and powerful feature of SQL that enables database users
to format the values stored in the tables. The following tasks are achieved using
functions:

          Performing calculations on data values

          Modifying the presentation format of data values

          Formatting groups of rows to give a single output

          Converting datatypes such as character(CHAR) to date(DATE)

SQL Function Types

SQL functions are of two types:

          Single-row functions: These functions format only single rows and return
            one result for each row.

          Multiple-row (or group) functions: These functions operate on groups of
            rows and return one result for each group of rows.

Single-row Functions

Single-row functions operate on single rows returning one value for every row
fetched by the query. Single-row functions can be used in SELECT, WHERE and
ORDER BY clauses. The syntax for issuing single-row functions is:
        <function_name> (column | expr [, arg1, arg2, …])
Where,
function_name is the name of the function.
column is the database column name.
expr is any literal character string or calculated expression.
arg1, arg2 are arguments passed into the function.

Arguments mean:

          Any constant or variable value

        Any column name or expression
A function may accept one or more arguments. However, the data value it returns
may be of a different datatype than what it was when referenced. For instance, a
function may accept an argument of character datatype but return a data value of
number datatype.
Single-row functions are of different types. They are as follows:

© SQL Star International Ltd.                                                     131
   Character functions

         Number functions

         Date functions

         Conversion functions

         General functions

Character Functions

Character functions format character data values by accepting them as inputs and
returning either character or number values as output. Character functions are
further divided into two categories, case conversion functions and character
manipulation functions.

Case Conversion Functions

These functions convert the case of the character data depending on the
requirement. The following are the case conversion functions:




Look at the following SELECT statement to identify the output derived using
conversion functions:

      SELECT UPPER(cFirstName)||
      ‗enrolled as member on ‘||dMembershipDt ―Member Details‖
      FROM Member;
The query result is as follows:




© SQL Star International Ltd.                                               132
-----------------
21 rows selected.
The usage of conversion functions is widely felt in the WHERE clause. For example,
the following SELECT statement is issued to retrieve books written by John Grisham:

      SELECT cBookName
      FROM Book
      WHERE cAuthorName = ‗JOHN GRISHAM‘;
      The above query displays the following message:
      no rows selected.

You will notice that this statement does not return any rows because the WHERE
clause mentions the author name as ‗JOHN GRISHAM‘. But in the Book table all
author names and book names are not stored in upper case, therefore, the name
‗JOHN GRISHAM‘ does not find an exact match in the table. This could be overcome
using case conversion function as follows:

      SELECT cBookName
      FROM Book
      WHERE UPPER(cAuthorName) = ‗JOHN GRISHAM‘;




Character Manipulation Functions

These functions manipulate character data and return either character data or
number data. Following are the character manipulation functions:




              Function                                   Functionality
CONCAT(column1| expr1,                   Joins the first argument (character value)
column2| expr2)                          to the second. It is the same as the
                                         concatenation operator (||) except that
                                         you are limited to using only two
                                         arguments.

© SQL Star International Ltd.                                                   133
E.g. CONCAT(‗Break‘, ‗fast‘) - Breakfast
SUBSTR(column| expr, m, [n])              Extracts characters (from the character
                                          value) of n character length starting from
                                          the character position m. In case you omit
                                          n, it extracts the characters till the end of
                                          the string.
                                           E.g. SUBSTR(‗Function‘,1,3) - Fun

                                          SUBSTR(‗Star‘,2) – tar Incase, m is
                                          negative it starts the count from the end
                                          of the character value.
                                          E.g. SUBSTR(‗Stars‘,-1) – s
LENGTH(column| expr)                      It returns the length of the character
                                          value. The result is a numeric value. E.g.
                                          LENGTH(‗Sqlstar‘)–7
INSTR(column| expr, m)                    It returns the numeric position of
                                          character m in the character string. E.g.
                                          INSTR(‗Sqlstar‘, ‗t‘) – 5
LPAD or     RPAD(column|     expr,   n,   It pads character values left justified or
‗string‘)                                 right justified using string to n character
                                          position width
                                          E.g. LPAD(8000,10, ‗*‘)- ******8000
                                          RPAD(‗8000‘,10, ‗*‘) – 8000******
TRIM(leading| trailing |both FROM         It trims leading or trailing characters or
trim_source)                              both from source text. In the e.g. it trims
                                          the leading ‗F‘ in the start of the character
                                          string ‗FIT‘
                                          E.g. TRIM (‗F‘ FROM ‗FIT‘) – IT.
REPLACE(text,search_string, character     Replaces the specified text expression
replacement_string)                       found in a string with the specified
                                          replacement string.
                                          E.g. REPLACE(‗SQLsTAR,‘s‘,‘S‘)- SQLSTAR
TRANSLATE(string1, string_to_replace,     Replace the 1st character in the
replacement_string)                       string_to_replace with the 1st character in
                                          the replacement_string.
                                          E.g. TRANSLATE(‗SQLSTAR,‘STR‘, ‗3it‘)-
                                          3QL3iAt

Display the first and last names as a single name of members whose first name
starts with ‗A‘. Display the length of the cFirstName column and find out the
numeric position of the vowel ‗e‘ in the first name. Issue the following SELECT
statement to see the output derived:

       SELECT CONCAT(cFirstName,cLastName) ―Name with A‖,
       LENGTH(cFirstName) Len,
       INSTR(cFirstName, ‗e‘) Instr
       FROM Member
       WHERE SUBSTR(cFirstName,1, 1) = ‗A‘;

The query result is as follows:




© SQL Star International Ltd.                                                      134
This statement displays following data for those members whose first names start
with A:
        Members first name joined with their last names
        The length of their first names
        The numeric position of the alphabet ‗e‘ in their first names.




Number Functions

Number functions accept number values as input and return only numeric values as
output. Following are the types of number functions:




© SQL Star International Ltd.                                               135
To understand the usage of NUMBER functions, use the examples mentioned above
in SELECT statements from the DUAL table.
       SELECT ROUND (67.238,2) ROUND,TRUNC (67.238,2) TRUNC
       FROM DUAL;



      SELECT CEIL(67.8)CEIL,FLOOR(67.8) FLOOR
      FROM DUAL;




Date Functions

In the Oracle database, dates are stored in an internal numeric format, which
represents the century, year, month, day, hours, minutes and seconds.
The default display for any date is DD-MON-RR. For example, the membership date
of the member Austin is displayed as 12-OCT-90. However, the date is not stored in
the database in this format. There is also time and century information associated
with it. The complete date might be October 12th, 1990 10:30:55 a.m.
Date functions accept date values and return a date or number datatype value.
Following are the date functions:


© SQL Star International Ltd.                                                 136
In addition to the functions mentioned above, you have the ROUND and TRUNC
number functions, which can be used with dates too.
ROUND (date, ‗fmt‘) – it rounds the date to the format model specified (month or
year). It rounds the date to the nearest day if the format is omitted. Given below are
some examples:

       ROUND (‘16-FEB-99’, ‘MONTH’) ->01-MAR-99
       ROUND (‘16-FEB-99’, ‘YEAR’) ->01-JAN-99

Syntax for the TRUNC function is:

       TRUNC (date, ‗fmt‘)

Examples for the same are:

       TRUNC (‗16-FEB-99‘, ‗MONTH‘) ->01-FEB-99
       TRUNC (‗16-FEB-99‘, ‗YEAR‘) ->01-JAN-99

After having understood the functionality of the various DATE functions, look at their
usage in the SELECT statement that follows.
Suppose the New Jersey Central Library management requests a complete report,
displaying the following details of all those persons who have been the members of
the library for greater than a year:

          Number of months the person has been the member of the library and

          Number of months after which his/her membership is to be renewed


      SELECT cMemberID,dMembershipDt ―Date‖,
© SQL Star International Ltd.                                                     137
MONTHS_BETWEEN(SYSDATE, dMembershipDt) ―Membership Period‖,
           ADD_MONTHS(dMembershipDt, 24) ―Renew Date‖
           FROM Member
           WHERE MONTHS_BETWEEN(SYSDATE, dMembershipDt)>12;




On issuing the query on member table, the following result is displayed:




-------------------------------------
21 rows selected




SYSTIMESTAMP:



SYSTIMESTAMP returns the system date, including fractional seconds and time zone
of the system on which the database resides. The return type is TIMESTAMP WITH
TIME ZONE.

The following example returns the system date.

           SELECT SYSTIMESTAMP FROM DUAL;

           SYSTIMESTAMP
           -----------------
           28-MAR-00 12.38.55.538741 PM -08:00



Performing Arithmetic Operations with Dates

Oracle stores dates as numbers in the database, therefore arithmetic operations
performed with dates produce the following results:



© SQL Star International Ltd.                                                138
 Adding a number to or subtracting a number from a date results in a date
value.
For example,
            SELECT (SYSDATE+ 2)
            FROM DUAL;




 Subtracting two dates results in the number of days between them.
For example, subtracting the current date from the membership date, returns the
number of days for which a person has been the member of the library.

      SELECT ROUND(SYSDATE-dMembershipDt) ―No of days‖, cMemberID
      FROM Member;
      The result of the statement is:




           -------------------------
           21 rows selected.



Conversion Functions

In an Oracle database, in addition to Oracle datatypes, other datatypes can also be
defined. In such a case, the Oracle server automatically converts them to Oracle
datatypes.
Similarly, the Oracle Server can convert one Oracle datatype to another Oracle
datatype. These datatype conversions are of two types: implicit conversion by the
Oracle server or explicit conversion by the user.




Implicit Datatype Conversion

While assigning values to a column, the assignment succeeds only when the Oracle
server converts the datatype of the value being assigned to that of the assignment
target.
For example, the nAge column of the Member table is of NUMBER datatype.
However, while assigning values to it, if you enter the age of a person in quotes
(‗24‘) it indicates that the value assigned is of CHARACTER datatype. In such a case
the Oracle server implicitly converts it to NUMBER datatype.
The Oracle server can automatically convert the following for assignments:



© SQL Star International Ltd.                                                    139
While evaluating expressions in the WHERE clause, the Oracle Server can
automatically convert CHARACTER values to NUMBER values provided the character
string represents a number.
For example, in the following statement the Oracle Server automatically converts the
number of copies entered in the WHERE clause to NUMBER datatype and displays the
desired result:

       SELECT cBookName
       FROM Book
       WHERE nNoOfCopies = ‗9‘;




      -----------
       9 rows selected.

Similarly, for expression evaluation, the Oracle Server automatically converts
CHARACTER value to DATE value provided the character string has the default date
format. You have witnessed this implicit conversion in a number of SELECT
statements written earlier.

For example,

       SELECT cFirstName,cLastName
       FROM Member
       WHERE dMembershipDt = ‘19-SEP-00';




Explicit Datatype Conversion

Datatype conversions can also be performed by the database developers or users,
for which SQL has provided the following three functions:




© SQL Star International Ltd.                                                   140
TO_CHAR Function

The TO_CHAR function is used to explicitly convert number and date datatype values
into character types. It converts NUMBER and DATE types to VARCHAR2.
The uses of TO_CHAR function are as follows:

 To display a number value as a character. The syntax for using the function with
numbers is:

       TO_CHAR (number, ‗fmt‘)

The syntax converts number values to character values using the format fmt
specified. The number formatting models are:




To understand the usage of the different number formats, look at the statement that
follows. The amount entered into the nFine column of the Transaction table is all of
number datatypes. But when you want to print a report displaying the amount the
library earns by way of fine, it would be more appropriate to prefix the amount with
a dollar symbol. This would require you to convert the values of the nFine column to
character datatype.


© SQL Star International Ltd.                                                     141
SELECT cTranID,dIssueDt, TO_CHAR(nFine, ‗$9999‘)Fine
       FROM Transaction
       WHERE nFine IS NOT NULL;

The query displays the following result:




          ------------------
           19 rows selected.
Points to remember while using TO_CHAR function with numbers:

          If the number of digits exceeds that provided in the format model, then
            pound signs (#) are displayed in its place.

        The decimal values are rounded to the number of decimal spaces provided
          in the format model.
To convert date from the default format of DD-MON-YY to the format you specify.
The syntax for using TO_CHAR function with dates is:
       TO_CHAR (date, ‘fmt’)
This syntax converts the DATE data to the format fmt specified. The date format
models are:

  Format                                    Description
CC or SCC     Century. Using S places a minus sign before BC
BC or AD      BC/AD indicator
B.C. or       BC/AD indicator with periods
A.D.
YEAR or       Year spelled out. For example, the year 2001 spelled as TWO THOUSAND
SYEAR         ONE
YYYY or       Year complete with all the four digits => 2001
SYYYY
YYY or YY     The last three, two, or one digits of the year => 001, 01,1
or Y
Q             Quarter of year – January through March=>1

MONTH         Name of the month with blanks to pad a length of nine
              characters => DECEMBER
MON           Three letter abbreviation of the month name =>DEC for DECEMBER
MM            Month as a two digit value – 12 represents the month DECEMBER
RM            Month as a roman numeral
WW            Week of year (numeric representation)
W             Week of month
DAY           Name of the day (Friday) with blanks to pad a length of nine characters
DDD           Day of the year – 001 stands for Jan 1, 032 for Feb 1
DD or D       Day of the month (01-31) and day of the week (1-7)
DY            Three letter abbreviation of the name of the day – Fri, Sat

© SQL Star International Ltd.                                                     142
J             Julian day stands for the number of days since 31 December 4713 BC
TH            Placed after any day of the months and are called ordinal number.E.g. for
              4TH write DDTH
SP            It is used to spell out a day and is called spelled-out number
              E.g: for Four- Write SPDD
SPTH          Spelled-out ordinal number. E.g for Fourth write DDSPTH
AM or PM      Meridian indicator
A.M. or       Meridian indicator with periods
P.M.
HH or         Hour of the day, or hour (1-12) or (0-23)
HH12 or
HH24
MI            Minute (0-59)
SS            Second (0-59)

Following guidelines need to be followed while using TO_CHAR with dates:

          You need to enclose the format model in single quotation marks.

          Format models are case sensitive.

          Any of the valid date formats can be included as the format model.

          Use a comma to separate the date value from the format model.

          The output is padded with blanks. Use the fm (fill mode) element to
            remove the padded blanks.

        By default the resultant column width is 80 characters.
On issuing a SELECT statement to retrieve the membership dates of members, the
dates are retrieved in the default date format. To convert it use the TO_CHAR
function as follows:

       SELECT cFirstName||cLastName NAME,
       TO_CHAR(dMembershipDt, ‗fmDdSPTH ―of‖ Mon YYYY‘) ―Membership Date‖
       FROM Member;

The query displays the following result set:




-----------------
21 rows selected.
The result displays the membership date as the format model specified. Notice that
the day is spelled with the first letter capitalized and rest in lower cases, the month
displayed as a three-letter abbreviation with the first letter capitalized, and the year
displayed complete with four digits.

© SQL Star International Ltd.                                                       143
In addition to the above mentioned date formats, there is a RR format. The RR
format is explained below. The RR date format is similar to the YY format except that
the century of the return date varies according to the specified two-digit year and
the last two digits of the current year. Therefore, RR format allows you to specify
different centuries.




The following table illustrates the way the RR element behaves:




Suppose you enter your date of birth as 20-JAN-79 (where the year of birth is 1979),
then Oracle interprets it as 20th Jan 2079 (according to YY format). This is incorrect.
However, with the RR format, it will be interpreted as:




TO_NUMBER and TO_DATE Functions

To convert a character string to a number or a date you need to use TO_NUMBER
and TO_DATE function. For conversion use the format models previously explained.
To convert a character string to number or date, the following syntax is used:

       TO_NUMBER (char, ‗fmt‘)
       TO_DATE (char, ‗fmt‘)

© SQL Star International Ltd.                                                      144
Suppose the user querying the Member table is unaware of the default date format,
then while retrieving the IDs of members enrolled on 13 th March 1989, he/she would
issue the following SELECT statement:

       SELECT cMemberID
       FROM Member
       WHERE       dMembershipDt = ‗March 13,1989‘;

And encounter the following error message:
      ERROR at line 3:
      ORA-01861: literal does not match format string

This SELECT statement is erroneous because the date entered in the WHERE clause
is not in its default format. This can be rectified using the TO_DATE function as
follows:
       SELECT cMemberID
       FROM Member
       WHERE dMembershipDt = TO_DATE (‗March 13,1989‘, ‗Month dd,YYYY‘);

The result is now correct as given below:




General Functions

General functions work with any datatype and comprise of the following:

          NVL function

          NVL2 function

          DECODE function

          The CASE expression, which comprises:

               •   Simple CASE expression

               •   Searched CASE expression

               •   NULLIF

               •   COALESCE



NVL Function

Performing calculations with null values result in null values. This situation can be
overcome using the NVL function.
NVL function converts a null value to a specified value. This function can be used
with any datatype be it character, number, or date. Its syntax is:


© SQL Star International Ltd.                                                    145
NVL (expr1, expr2)
Where,
expr1 is the column containing null value
expr2 is the value for converting the null value
The datatypes of both expr1 and expr2 must match.
While issuing a SELECT statement to retrieve details of members, some of the values
of the cPhone and cEmailID columns may be null. Rather than leaving them as
null, you can use the NVL function to display a suitable text in place of the null value.

       SELECT cMemberID,NVL(cPhone,‘not known‘)Phone
       FROM Member;

On executing this statement, the text ‗not known‘ would be displayed for all those
members whose phone numbers are unknown.




              ---------------
          21 rows selected.




NVL2 Function

The NVL2 function returns the result based on its examining the first expression. If
the first expression is not null, the function returns the second expression. If the first
expression is null, the function returns the third expression. The syntax of NVL2
function is as follows:

        NVL2 (expr1, expr2, expr3)
Where,
expr1 is the expression that may or may not contain null
expr2 is the expression returned in case expr1 is not null
expr3 is the expression returned in case expr1 is null
While retrieving transaction details of members, their fine status could be made
more descriptive, such that if fine is null, the text ―No fine dues‖ is displayed, and if
fine is not null, the text ―Defaulter – fine due‖ is displayed. To achieve this, the
following SELECT statement is to be written:

       SELECT cMemberID, dIssueDt,
       dActualReturnDt, nFine,
       NVL2(nFine,‘Defaulter - Fine due‘,
       ‗No fine due‘) ―Fine Status‖
       FROM Transaction;

The result of the query is:




© SQL Star International Ltd.                                                         146
----------------
31 rows selected.




DECODE Function

The functionality of DECODE is similar to that of IF-THEN-ELSE logic used in most of
the programming languages.
Its syntax is:
       DECODE (column / expr, search1, result1
                           [, search2, result2,…,]
                           [, default])

The DECODE function compares the expr or the column values to each of the search
values and returns the result if the expr is same as the search value. If we omit the
default value, it returns a null value wherever the expr does not match the search
value.
Suppose the library increases the stock of books, but by different quantities for its
branches, the same could be illustrated using the DECODE function as follows:

       SELECT cBranchID, nNoOfCopies,
       DECODE (cBranchID, ‘01ADLNJ‘, nNoOfCopies+1,
       ‘02CHSNJ‘,nNoOfCopies+2, nNoOfCopies) ―revised copies‖

       FROM Book
       WHERE cBranchID IN (‘01ADLNJ‘,‘02CHSNJ‘);
The result of the query is.




----------------

© SQL Star International Ltd.                                                    147
70 rows selected.
In the statement, the cBranchID value has been decoded, that is,

          If branch ID is 01ADLNJ, the number of copies is increased by 1

          If branch ID is 02CHSNJ, the number of copies is increased by 2

          In case of all other branches the number of copies is to remain the same.




The CASE Expression

CASE expressions use IF-THEN-ELSE logic in SQL thereby facilitating conditional
inquiries. The SQL: 1999 standard has the following four types of CASE expressions:

          Simple CASE expression

          Searched CASE expression

          NULLIF

        COALESCE
Simple CASE Expression
The simple CASE expression is similar to the DECODE function. It does not support
comparison operators. Its syntax is as follows:

       CASE expr WHEN comparison_expr1 THEN return_expr1
               WHEN comparison_expr2 THEN return_expr2
                WHEN comparison_exprn THEN return_exprn

       ELSE else_expr
       END

The CASE expression functions as follows:
The Oracle server searches for the first WHEN…THEN pair for which expr is equal to
comparison_expr, and returns return_expr.
In case none of the WHEN…THEN pairs meet this condition, and if an ELSE clause
exists, then Oracle server returns the else_expr, otherwise it returns null. [The literal
NULL cannot be specified for all return_exprs and else_exprs, and all the expressions
must be of the same datatype]
The Library management decides to revise the member fee structure as follows:
If grade is ‗A‘ then increase the fee by 5%
If grade is ‗B‘ then increase the fee by 10%
If grade is ‗C‘ then increase the fee by 15%
For all other grades there is no increase in fee
The effect of implementing the above changes could be viewed by writing the
following SELECT statement making use of the CASE expression:

       SELECT cGrade,nFeeAmount,
             CASE cGrade
                   WHEN ‗A‘ THEN nFeeAmount*1.05
                   WHEN ‗B‘ THEN nFeeAmount*1.10
                   WHEN ‗C‘ THEN nFeeAmount*1.15
© SQL Star International Ltd.                                                        148
ELSE nFeeAmount
            END ―Revised Fee‖
       FROM MemberFee;

The result of the query is:




Searched CASE Expression

Searched CASE expression can conditionally be used to search and replace values
within expressions. Comparison operators can be used in the conditional expression.
Searched CASE expressions are more flexible than simple CASE expressions because,
within searched CASE expressions, each WHEN condition can be different and
multiple conditions can be combined with logical operators.
For example, look at the following query:
       SELECT cBookName,cCategoryID,nNoOfCopies,
       CASE WHEN cCategoryID LIKE ‗__%FIC‘ THEN nNoOfCopies+2
            WHEN cCategoryID LIKE ‗__%ROM‘ THEN nNoOfCopies+1
            WHEN cCategoryID LIKE ‗__%NFI‘ THEN nNoOfCopies+3
            WHEN cCategoryID LIKE ‗__%SFI‘ THEN nNoOfCopies+4
            WHEN cCategoryID LIKE ‗__%MYS‘ THEN nNoOfCopies+1
                      ELSE nNoOfCopies
              END ―Revised Copies‖
       FROM Book
       WHERE cBranchID=‘03HAMNJ‘;

In the query, you are trying to determine the revised number of copies of books
based on the book categories for branch ‗03HAMN‘ as follows:

          If category is ‗FIC‘ then increase copies by 2

          If category is ‗ROM‘ then increase copies by 1

          If category is ‗NFI‘ then increase copies by 3

          If category is ‗SFI‘ then increase copies by 4

          If category is ‗MYS‘ then increase copies by 1

       For all other categories there is no increase in the number of copies
The query generates the following result:




© SQL Star International Ltd.                                                    149
----------------
39 rows selected.

NULLIF Function
The NULLIF function compares two expressions. If the first expression is equal to the
second, the function returns NULL. If they are not equal, the function returns the
first expression. The syntax of NULLIF is:
        NULLIF (expr1, expr2)
Where,
expr1 is the expression compared to expr2, and is the expression returned in case
the two expressions are not equal. [The literal NULL cannot be specified for expr1]
expr2 is the expression compared to expr1
The semantics of the NULLIF expression is defined as follows:
        CASE
               WHEN expr1=expr2 THEN NULL
               ELSE expr1
        END

The NULLIF function can be used while querying the Transaction table, in a way
that by comparing the return dates with their actual return dates helps determine
whether books were returned on the return date set or at a later date.

       SELECT cMemberID, dReturnDt,
       dActualReturnDt,NULLIF(dActualReturnDt,dReturnDt)‖Result‖
       FROM Transaction;


On executing the query, the following result is generated wherein, the result displays
null if dReturnDt and dActualReturnDt are equal, and displays the actual return
date if they are not equal:




     -----------------
© SQL Star International Ltd.                                                     150
32 rows selected.




COALESCE Function

The COALESCE function is a generalization of the NVL function. However, its
advantage over the NVL function is that it can take multiple alternate values.
The COALESCE function accepts any number of expressions, and returns the first
non-null expression in the list.
If the first expression is not null, the function returns it, or else, it does a coalesce of
the remaining expressions. The syntax of The COALESCE function is:
        COALESCE (expr1, expr2, …, exprn)
Where,
expr1 is returned if it is not null.
expr2 is returned if expr1 is null and this expression is not null.
exprn is returned if the preceding expressions are null.

The semantics of the COALESCE expression is defined as follows:

          When the expression has exactly two arguments
            CASE
                 WHEN expr1 IS NOT NULL THEN expr1
                  ELSE expr2
            END


          When the expression has three or more arguments
            CASE
                  WHEN expr1 IS NOT NULL THEN expr1
                  ELSE COALESCE (expr2, expr3,…,exprn)
            END

The following query makes use of the COALESCE function:

       SELECT cTranID, dReturnDt, dActualReturnDt,
       COALESCE(dActualReturnDt,dReturnDt,sysdate) ―Returned‖
       FROM Transaction;

In the above SELECT statement, if the actual return date(DACTUALRETURNDT) is
not null, it is returned. If the actual return date(DACTUALRETURNDT) is NULL, then
the return date (DRETURNDT) is displayed provided it is not null. If both
DACTUALRETURNDT and DRETURNDT are null, then SYSDATE is displayed as shown
below.




Summary

In this chapter, you have learnt that:

                      Functions are built-in programs that accept arguments and
                       return a value.
© SQL Star International Ltd.                                                          151
   Data in the database can be retrieved using SQL functions in a
                     desired manner.             These functions accept arguments
                     of different data type such as character, data         and
                     number, returning a single output for each row. Hence they are
                     known as Single Row functions.

                    While retrieving the character information, case of a character
                     can be controlled
                    using Case Manipulation functions and specific information from
                     these characters can be extracted using Character Manipulation
                     functions.

                    Number functions can be used to work with number data which
                     accept number             values as input and return only
                     numeric values as output.

                    Date Functions are used to work with Date data and returns
                     number as well as date output.

                    In case of Incompatibility of data, conversion function such as
                     TO_CHAR, TO_NUMBE and TO_DATE are used to explicitly
                     convert data to specific datatypes. Implicit conversions are
                     handled by Oracle server itself.

                     NULL values can be handled using a set of functions
                     which are categorized under the general functions. Using these
                     function one can improve the logic of the programs.




Lab Exercise
1.    Write a query to display:

           The last name in uppercase

           The length of the last names

        Job IDs starting from the fourth character.
      The output should be as shown below.




© SQL Star International Ltd.                                                   152
----------------
                 107 rows selected.
2.     Write a query to display employee ID, first name, salary and salary increased
by 10%, which is expressed as a whole number. Name the column as ‗New_Sal‘.
3.     Write a query to display the first name and number of months worked by the
employees. Round the number of months worked to the closest whole number. Sort
the result by the number of months employed. The output should be as shown
below.




4.     Write a query to display the employee ID, hire date, and salary. The hire date
should appear as (For E.g.) ‗Seventh of June 1994 12:00:00 AM‘. The salary should
appear as $15,000. Give each column an appropriate label as shown below.




5.     Write a query to display the employee ID, hire date and salary review date.
The salary review date is the first Friday after a year of service. Name the column as
‗Salary Review Dt.‘. The salary review dates should appear as ‗Friday, 31 st of July,
2000‘.




© SQL Star International Ltd.                                                     153
6.     Write a query to retrieve the last name and hire date of employees hired
before 1994. The query should return the same result even if the query is run in
1994 or now.

7.      Write a query to retrieve the employee ID, salary, commission, and annual
salary, which is calculated by multiplying salary by 12, and then adding the
commission percentage to the result. Annual salary is to be calculated for all
employees irrespective of whether they earn a commission or not.

       The query result should be as shown below.




8.    Write a query to retrieve the employee ID, job ID and salary of all employees.
The query should calculate increase in salary on the following basis:

 If job ID is ‗SA_REP‘, salary increase is 10%

 If job ID is ‗ST_CLERK‘, salary increase is 15%

 If job ID is ‗IT_PROG‘, salary increase is 20%

 For all other job IDs, there is no salary increase.
Perform the above query using CASE expression as well as DECODE function.




© SQL Star International Ltd.                                                   154
Chapter 7




                                Working with Grouped Data
                                      Explain the various group functions
                                               Use of NULL value function
                                                 Use of GROUP BY clause
                                                   Use of HAVING clause




© SQL Star International Ltd.                                        155
Objectives

At the end of this chapter, you will be able to:

Use     Group functions

Use     GROUP BY clause

Restrict       the groups using HAVING clause




Introduction
As we have seen earlier, SQL Functions are broadly categorized into two types,
Single row functions and Multiple row functions. We are familiar with the working of
single row function and its use. Let us now, look into the second category of the
functions-Group functions.
What are these group functions and why do we need them?
To explain the above question, let me relate a scenario. Suppose an organization
wants to calculate the total salary expenditure incurred for a particular month. Since,
the calculation has to be done on a collective data, we need to use Group Functions.
Further, if they need to know what is the salary disbursed in each department, the
table has to be split into groups and then, the Group Functions need to be applied on
it.
So, Group Function performs data operations on sets (or groups) of rows. The set
may be the whole table or table split into groups. It gives one result per group.
Group functions differ from single row functions, in that, they can manipulate several
rows at a time. This helps in obtaining summary details such as averages, sum,
maximum or minimum.




Group Functions
There are different group functions available. Some of them are:

          AVG

          SUM

          MAX

          MIN

          COUNT


© SQL Star International Ltd.                                                      156
AVG Function

This function returns the average value of columns with numeric values. Its syntax
is:
       AVG ([distinct| all] x)

It returns the average value of the values of column x, ignoring null values.
Where,
distinct is used in order to consider only non-duplicate values.
all is the keyword that causes the function to consider even duplicate values. This is
the default and hence, need not be mentioned.
For example, to calculate the average fine amount earned by the library, the
following statement is issued:

        SELECT AVG(nFine) FINE
        FROM Transaction;
Output:
        FINE
        --------
        5.475
But this statement ignores null values and calculates the average fine by dividing the
total fine amount by the number of people who have paid the fine. Therefore, use
the NVL function to include null values. Now, notice the difference in the average fine
amount.
        SELECT AVG(NVL(nFine, 0)) FINE
        FROM Transaction;
Displays:
        FINE
    --------
        3.421875




SUM Function

This function returns the total or sum of given values. Its syntax is:
       SUM ([distinct|all] x)
Which returns the sum of all the values in column x, ignoring null values.
For example, to calculate the total number of copies of books stored in branch
‗04RANNJ‗ the following SELECT statement is issued:
       SELECT SUM(nNoOfCopies) TOTAL
       FROM Book
       WHERE cBranchID = ‘04RANNJ‘;
Displays:
       TOTAL
       --------
    165

MAX and MIN Functions

These functions return the maximum and the minimum values respectively for any
given expression. You can use these functions for any datatype unlike AVG and SUM.
Their syntax is:

© SQL Star International Ltd.                                                      157
MAX ([distinct|all] x)
       MIN ([distinct|all] x)

Which returns the maximum and the minimum value for column x, ignoring null
values.
For example, in order to determine the senior most and junior most members of the
library based on their age as well as on their membership dates, issue the following
SELECT statement:

       SELECT MAX(nAge) Oldest,
       MAX(dMembershipDt) JuniorMem,
       MIN(nAge) Youngest,
       MIN(dMembershipDt) SeniorMem
       FROM Member;
Displays:




COUNT Function

There are two formats for COUNT function. They are:
       COUNT (*)
       COUNT (column_name)
COUNT (*) returns the total number of rows in a table including both the duplicate
rows as well as those rows containing null values in any of the columns.
In case a WHERE clause is included in the SELECT statement, the function returns
the count of only those many rows that satisfy the WHERE condition.
For example, to retrieve the total number of members whose age is above twenty,
issue the following statement:

       SELECT COUNT (*)
       FROM Member
       WHERE nAge > 20;
The query displays the following result:
       COUNT(*)
       -------
       10
Using of COUNT (*) is not recommended because the processing mechanism is very
slow, as it has to first resolve all column names in the table. This step is unnecessary
when you need to know only the number of rows in a table. Instead, use COUNT (1)
or
COUNT (ROWID). A ROWID is a pseudo-column. It is not a part of the table. Rather,
they are unique numbers generated by the server to identify each row uniquely and
they are stored internally within Oracle.
COUNT (column_name) on the other hand, returns the number of rows in a table,
but excludes rows with null values in the column identified by column_name.
For example, to display the number of members who have paid fine for books issued
on ‗08-AUG-2000‘, issue the following statement:

       SELECT COUNT (nFine)
       FROM Transaction
       WHERE dIssueDt = ‘08-AUG-2000';
Displays:

© SQL Star International Ltd.                                                       158
COUNT(NFINE)
       --------
       2
The result gives a total of two rows (instead of three) because one of the members
who had issued books on ‗08-AUG-2000‘ did not have to pay fine as they had
returned the books on the due dates.




Creating Logical Groups of Data

Till now you have used group functions, which treat the entire table as one group.
But, you may need to collect summarized details for different groups within the same
table. For example, finding the total number of books stored in a library can be done
using the COUNT function in a simple SELECT statement as shown below.

        SELECT COUNT (cBookName)
        FROM Book;
Displays:
        COUNT(CBOOKNAME)
        ---------------
        186
However, situations arise when you need to know the total number of books
belonging to different categories. In such a situation you have to group the books
based on the categories to which they belong. This is done using the GROUP BY
clause.
The GROUP BY clause divides the table into smaller groups. Its syntax is:

       SELECT column, group_function (column)
       FROM table
       [WHERE condition]
       [GROUP BY group_by_column]
       [ORDER BY column];
Where,
column is the individual column you want to select.
group_function (column) is the column on which a group function has been applied.
Group_by_column specifies those columns whose values will form the basis for
splitting the table into groups of rows.
There are certain points to remember while using the GROUP BY clause:
        In order to select individual columns (columns that are not an aggregate
function)       along with the column specified within the group function, place the
individual columns            in the GROUP BY clause.
For example, to retrieve the total number of books grouped according to their
categories, if you type the following:
         SELECT cCategoryID, COUNT(cBookName)
         FROM Book;

© SQL Star International Ltd.                                                    159
You get an error:
            ERROR at line 1:
            ORA-00937: not a single-group group function.
 Use the WHERE clause before dividing rows into groups.
 Column alias cannot be used in the GROUP BY clause.
 Group functions can be used in the ORDER BY clause.
The following SELECT statement explains how to retrieve the total number of books
grouped according to their categories:

      SELECT cCategoryID, COUNT(cBookName)
      FROM Book
      GROUP BY cCategoryID;
And the result is:




    -----------------------
     14 rows selected.
In the above example, the SELECT clause contains the columns to be retrieved i.e.
the book category IDs and the total number of books in each of the categories. The
FROM clause contains the table that needs to be accessed i.e. the Book table. The
GROUP BY clause specifies how the rows are to be grouped. The rows are grouped
based on the category to which they belong.
The same example could be rewritten as follows:

       SELECT COUNT(cBookName)
       FROM Book
       GROUP BY cCategoryID;

In this statement, the column specified in the GROUP BY clause is not contained in
the SELECT list, yet it displays the number of books belonging to different categories.
This shows that the GROUP BY column need not be in the SELECT list. But the results
do not look meaningful.
So far we have grouped rows based on one column, but you may need to display
results for groups within groups. For example, to find the total number of books
published, each year grouped by category, you would first need to group the table by
book category, and within that group, you would need to group by publishing year.

       SELECT cCategoryID,dPublishedYr Published,
       COUNT(cBookName)‖Total Books‖
       FROM Book
       GROUP BY cCategoryID, dPublishedYr;

The result of the query is:




© SQL Star International Ltd.                                                      160
------------------------------------
45 rows selected.




Restricting Grouped Data

Suppose you are interested in finding the total number of books belonging to each
category, but display only those categories, which have more than 10 books
belonging to them. In such a case, you need to put restriction on the groups.

       SELECT cCategoryID, COUNT(cBookName)
       FROM Book
       WHERE COUNT(cBookName)>10
       GROUP BY cCategoryID;
This statement gives you an error at the following statement:
       WHERE COUNT (cBookName)>10
              *
       Error at line 3
       ORA-00934: group function is not allowed here

This statement gives rise to the following error: ‗group function is not allowed here‘,
indicating that you cannot use group functions in the WHERE clause.
Instead you need to use the HAVING clause. By using the HAVING clause you specify
the groups that need to be displayed.
You can place the HAVING clause before the GROUP BY clause, but it is more logical
to place the GROUP BY clause before because you first form the groups, then
perform the group functions.

       SELECT cCategoryID,COUNT(cBookName)‖No. of Books‖
       FROM Book
       GROUP BY cCategoryID
       HAVING COUNT(cBookName)>10;
The result of the query is:




© SQL Star International Ltd.                                                      161
------------------
10 rows selected.




Summary
In this chapter, you have learnt that:

   Group function takes a collective data for its operation and returns a single
   value. The function can act upon character, number and date datatypes
   respectively.

       The functions discussed in this chapter are sum(), avg(), min() , max() and
   count(). NULL values are ignored in all these functions except count (*).
    To get a group wise resultant, the table is split into groups using GROUP BY
   clause. Groups can be based on one or more columns.
       In order to select individual columns (columns that are not an aggregate
   function) along with the column specified within the group function, place the
   individual columns in the GROUP BY clause.
        Using WHILE clause, one can restrict the number of rows used in the
   formation of the group.
      Using HAVING clause, one can restrict the groups to be included in the final
   resultant.




© SQL Star International Ltd.                                                        162
Lab Exercise
1.     Write a query to display the maximum, minimum, sum, and average salaries
for each job type. The query result should be as shown below.




   2.     Write a query to display the number of employees belonging to the same
          department numbers. The query output should be as follows:




           12 rows selected.
3.     Write a query to display the manager ID and the highest paid employee for
that manager. Exclude employees who do not have a manager.
4.     Write a query to display the job ID and total salary for each job that has total
salary exceeding $13000.




© SQL Star International Ltd.                                                      163
Chapter 8




                                                        Joins
                                             Introduction to Joins
                                        Discuss the Need of Joins
                                                    Types of Joins
                                           Oracle Proprietary Join
                                           SQL: 1999 syntax Join
                                Three way Join with the ON clause
                                              Using Set operators




© SQL Star International Ltd.                                 164
Objectives


At the end of this chapter, you will be able to:

   Identify the need for joins

  Obtain data from multiple tables using Oracle proprietary
     syntax

  Obtain data from multiple tables using SQL:1999 syntax

  Use Set operators




© SQL Star International Ltd.                                    165
Introduction to Joins
Organizations usually have large databases consisting of many tables. It is not
functionally efficient to have a single table storing all data. In the process of their
business, organizations require to prepare reports by extracting data that may be
from one or more than one table. You can retrieve data from more than one table by
creating joins. Joins are query statements made on more than one table using a
column, which is common to both tables.
Retrieving Data from Multiple Tables
View the report shown below to understand the use of a join:




The report displays names of books and their publishers. The book names are
derived from the Book table, where as the publisher names are derived from the
PublisherDetails table.
In order to join these two tables there must exist a relationship between them. For
instance, Book and PublisherDetails tables in the library database are related
through the column cPublisherID. You can query for the names of the books and
their publishers with a join as this column relates the two tables.
The syntax for creating a join is:

       SELECT table1.column, table2.column…
       FROM table1, table2
       WHERE table1.column1= table2.column2;

OR
       SELECT t1.column, t2.column…
       FROM table1 t1, table2 t2
       WHERE t1.column1= t2.column2;

Where,
SELECT table1.column, table2.column…


© SQL Star International Ltd.                                                      166
lists the columns that you want to be displayed along with any of the functions or
column alias.
FROM table1, table2 specifies the table where the data is stored.
WHERE table1.column1= table2.column2 specifies the condition that needs to be
met for the join to be created.
In a table join, the FROM clause contains two or more tables which are the source for
data. The WHERE clause contains comparison operations, which specify how data
from the tables are to be joined.

Guidelines for writing Join conditions

      The FROM clause contains names of more than one table each followed by an
        alias. This reveals an interesting aspect of Oracle. Not only the columns in the
        SELECT statement can have alias, but even the tables in the FROM clause can
        have aliases.

      Table alias must not be more than 30 characters in length.

       The table alias given for a table in the FROM clause must be used for the
        table name throughout the SELECT statement.

       The table alias is valid only for the current SELECT statement.

      Columns having common values in multiple tables may have the same column
        names. For instance, the column-containing publisher Ids has the name
        cPublisherID in both, the Book as well as the PublisherDetails table. This
        makes it easier to identify them as columns with similar data. However, this
        causes ambiguity as the Oracle SQL processing mechanism is unable to
        resolve the column names (from which table is the column being referred to)
        and therefore, would return an error. To avoid ambiguity, precede each
        column with the table name or the alias.

      You need not precede a column name with its table name or alias if it appears
        only in one of the tables specified in the FROM clause. But, by prefixing the
        table name or alias you would be able to enhance database access, as the
        server would know exactly, in which table the column resides.

     For joining n tables, you must have at least (n-1) join conditions. For
      instance, to join three tables there must be a minimum of two join conditions.
What is a Cartesian product?
A Cartesian product results in the display of a large number of rows, that is, all
combination of rows, where all rows in the first table are joined to all the rows in the
second table. A cartesian product is generated as a result of:

      Omitting a join condition

    Specifying an invalid join condition
The following example illustrates how a Cartesian product gets generated:
        SELECT cMemberID, nFeeAmount
        FROM Member,MemberFee;

The statement displays the following output:




© SQL Star International Ltd.                                                       167
----------------
84 rows selected.
The Member IDs and their fee amounts are displayed from the Member table and
the MemberFee table respectively. But since the WHERE clause has been excluded,
all rows from the Member table are joined with all the rows in the MemberFee
table returning 84 rows in the result.
In order to avoid a Cartesian product ensure that you have at least n-1 join
conditions in the SELECT statement for n joined tables. There must be one join
condition to avoid the Cartesian product.




Types of Joins
Tables are joined by including a join condition in the WHERE clause. There are
different ways of joining data.
The types of joins are:

      Oracle Proprietary Joins

              Equijoin

              Non-Equijoin

              Outer join

              Self join

      SQL:1999 Compliant Joins

              Cross joins

              Natural joins

              Using clause

              Full or two sided upper joins

              Arbitrary join conditions for outer Joins

© SQL Star International Ltd.                                              168
Obtaining Data from Multiple Tables

Prior to Oracle9i, you could obtain data from multiple tables using the ‗join‘
statement, which belongs to Oracle proprietary syntax. These ‗join‘ statements
include equijoin, non-equijoin, outer join and self join.
Creating Equijoins
Equijoins are also referred to as simple joins or inner joins. In an equijoin we make
use of the equality operator in the join condition. It returns data where column
values in one table equal that of the other table.
For example, in order to display the publisher‘s name for each book, you would have
to compare the publisher ID values in the Book table with the publisher ID values in
the Publisher table. There exists an equijoin relationship between the Book table
and the Publisher table, as the values in the cPublisherID columns of both the
tables are the same. This is executed with:

       SELECT B.cBookName, B.cPublisherID, P.cPublisherName
       FROM Book B, PublisherDetails P
       WHERE B.cPublisherID = P.cPublisherID;

Which displays the following result:




-------------------
     184 rows selected.
In the statement the SELECT clause retrieves book names and their publisher‘s ID
from the Book table and publisher names from the PublisherDetails table. These
tables are joined by the equijoin condition specified in the WHERE clause.
Additional Search Condition
The above example retrieved the publisher names of all the books stored in the
library by issuing a join condition in the WHERE clause. However, in addition to the
join, you may want some other restrictive condition to be specified in the WHERE
clause. For instance, retrieve the publisher names of the books written by ‗John
Grisham‘ and which are stored in the ‗Chester‘ branch of the library. You can specify
this additional criteria in the WHERE clause using the AND operator as follows:

       SELECT B.cBookName, B.cPublisherID,
       P.cPublisherName
       FROM Book B, PublisherDetails P
       WHERE B.cPublisherID = P.cPublisherID
       AND B.cAuthorName = ‗John Grisham‘
       AND B.cBranchID = ‘02CHSNJ‘;
The result of the query is:




© SQL Star International Ltd.                                                    169
So far you have joined only two tables, but it is also possible to join more than two
tables when the need arises.
For example, if the desk officer wants to display the category name and the publisher
name of books written by ‗Nora Roberts‘ stored in branch ‗05PRINJ‘, you would have
to join three tables, namely the Book table, the PublisherDetails table and the
Category table as follows:

       SELECT B.cBookName, C.cCategoryName,
       P.cPublisherName
       FROM Book B, Category C, PublisherDetails P
       WHERE B.cCategoryID = C.cCategoryID
       AND B.cPublisherID = P.cPublisherID
       AND B.cAuthorName = ‗Nora Roberts‘
       AND B.cBranchID = ‘05PRINJ‘;

The result of the query is:




Creating Non-Equijoins
A non-equijoin relationship is established when a column in a table does not directly
correspond to any column in the other table. To establish a non-equijoin relationship
you need to use operators other than equal (=), such as <=, >=, or BETWEEN.
For instance, based on the age of a person the library charges the membership fee.
The MemberFee table contains details about the amount of fee payable by people
falling within the range of ages specified. To display the different membership fee
amounts, age must be specified between a range as shown below.

       SELECT M.cMemberID, M.cFirstName,
       M.dMembershipDt,M.nAge,MF.nFeeAmount
       FROM Member M, MemberFee MF
       WHERE M.nAge BETWEEN MF.nLowerAge AND
       MF.nUpperAge;

The query displays the following result:




    ------------
    21 rows selected.

© SQL Star International Ltd.                                                    170
Creating Outer Joins

An outer join is used to retrieve data from multiple tables where information in one
of the joining columns is deficient compared to the same in the other tables. For
instance, querying the Book table will not display the list of books that have been
issued and those that have not, because the result of the query will not specify which
books have been borrowed. To identify which books have been issued and which can
be issued, you need to use an outer join.

The outer join operator is a plus sign enclosed in parentheses (+). You can place the
operator on either side of the WHERE clause condition, which ever is deficient in
data. That is, place it after the column, which does not have values that match
corresponding values in the other table. It denotes the creation of one or more null
rows in the deficient table that can be joined to the non-null rows of the non-
deficient table. But an outer join operator can appear only on one side of the
condition.
The syntax to create an outer join is:
        SELECT table1.column, table2.column
        FROM table1, table2
        WHERE table1.column (+) = table2.column
        [WHERE table1.column = table2.column (+)];
The situation mentioned above can be handled in the following way:
        SELECT T.cMemberID,B.cBookName
        FROM Book B, Transaction T
        WHERE B.cBookID = T.cBookID (+);
The result of the query is:




   -----------------
   186 rows selected.
From the output, you can identify all those books that have been issued by the
member ID, mentioned along with it. The books that are available but have never
been borrowed have no match in the transaction table and hence there is no
member ID mentioned along with it.

Creating Self Joins
A self-join is a join that is created while joining a table to itself. A self-join can be
created with a single table only. You can create a self-join when you want two kinds
of information from the same table or, in other words, you want the same data but
from two different angles.
This can best be explained by the following example:
In order to find the names of the superiors of each of the library staff members, you
would have to join the LibStaff table to itself.
The information contained in the LibStaff table is as follows:




© SQL Star International Ltd.                                                        171
7 rows selected.

From the details displayed in the LibStaff table, to find the immediate superior of
‗Matt Scummen‘, you would have to:
Identify ‗Matt Scummen‘ from the cLibStaffName column.
Identify the manager (or superior‘s) number for ‗Matt Scummen‘ from the
nLibMgrNo column. On identifying, you get the manager number as 104.
Identify the name of the superior having staff number as 104 from the
cLibStaffName column. The staff member having staff number as 104 is ‗Susan
Dudley‘. Therefore, ‗Susan Dudley‘ is ‗Matt Scummen‘s‘ superior.
To identify ‗Matt Scummen‘s‘ superior, you had to look at the LibStaff table twice.
First, to locate ‗Matt Scummen‘ and his superior‘s staff number. Second, to locate the
name of the superior having the staff number 104.
Rather than doing this manually, you could derive at the following result using self
join:
                   Subordinates                             and Their Superiors




To join LibStaff table to itself, you would have to issue the following SELECT
statement:

       SELECT Subordinate.nLibStaffNo,
       Subordinate.cLibStaffName, Subordinate.nLibMgrNo,
       Superior.nLibStaffNo, Superior.cLibStaffName
       FROM LibStaff Subordinate,LibStaff Superior
       WHERE Subordinate.nLibMgrNo=Superior.nLibStaffNo;

In the above self join, LibStaff table has been assigned two aliases, Subordinate
and Superior in the FROM clause. The join condition in the WHERE clause matches
the subordinates manager number with the staff number of the superior. The result
of the self-join is:




© SQL Star International Ltd.                                                     172
Obtaining Data from Multiple Tables using SQL: 1999
Syntax
Prior to Oracle9i, the Oracle database supported joins using the proprietary syntax.
The traditional join syntax has its limitations. In a complex query, it can be difficult
to parse the WHERE clause to separate the join condition from other restrictions
placed on the query results. In addition, the programmers sometimes overlook to
specify any join condition at all, leading to Cartesian product.
Support for SQL/99 standard join syntax was introduced in Oracle 9i.This support
makes it easier to write portable applications and enables full outer joins.
Types of SQL: 1999 Joins
To retrieve data from more than one table, you make use of the ‗join‘ statement. The
SQL: 1999 join syntax provides the following types of joins:

      CROSS JOIN

      NATURAL JOIN

      The INNER/OUTER JOIN

      FULL OUTER JOIN


The SQL: 1999 join syntax is as follows:
        SELECT table1.column, table2.column
        FROM table1
        [CROSS JOIN table2] |
        [NATURAL JOIN table2] |
        [JOIN table2 USING (column_name)] |
        [JOIN table2
        ON (table1.column_name = table2.column_name)] |
        [LEFT|RIGHT|FULL OUTER JOIN table2
        ON table1.column_name = table2.column_name)];



Where,
table1.column is the table and column from which the data will be retrieved.
CROSS JOIN retrieves a Cartesian product from the two tables.

© SQL Star International Ltd.                                                       173
NATURAL JOIN joins two tables, based on the same column name.
JOIN table USING column_name        – performs an equijoin based on the column
name.
JOIN table ON (table1.column_name = table2.column_name).
performs an equijoin based on the condition in the ON clause.
Cross Joins
The CROSS JOIN clause is used to retrieve the Cartesian product of two tables, which
is the cross product of two tables.

For example,
       SELECT cBookName, cCategoryName
       FROM Book CROSS JOIN Category;

The CROSS JOIN statement retrieves the names of books and categories from the
Book and Category tables. The keyword CROSS JOIN indicates that a Cartesian
product must be retrieved.
Natural Joins
A NATURAL JOIN takes into account all the columns in the two tables that have the
same name and the same datatype. In prior releases, to join two tables, you had to
explicitly specify the columns on which the JOIN was to be based. However, in case
of NATURAL JOINS you need not specify the column names explicitly. A natural join
is performed automatically based on all the columns in two tables that have same
name and same datatype. If you perform a natural join on two tables that have
columns with same names but different datatypes, a NATURAL JOIN syntax error is
returned.
When you perform a natural join on two tables, it selects rows that have equal
values in all the matched columns.
The keyword NATURAL JOIN is used to perform this type of join.
        SELECT cTranID, dIssueDt, cBookName, dActualReturnDt
        FROM Book NATURAL JOIN Transaction;

In the statement, Transaction table is joined to the Book table taking into account
cBookID column, which exists in both the tables. Had there been more common
columns, NATURAL JOIN would have used them.
The same result can be obtained using equijoin as follows:

      SELECT cTranID, dIssueDt, cBookName,dActualReturnDt
      FROM Book b, Transaction t
      WHERE b.cBookID = t.cBookID;
A Natural Join with WHERE clause

You can also use WHERE clause with a NATURAL JOIN to restrict the result of your
query.
       SELECT cTranID, dIssueDt, cBookName, dActualReturnDt
       FROM Book
       NATURAL JOIN Transaction
       WHERE cBookID IN (‗SFI050001993‘,‗NFI040000224‘, ‗HUM050001003‘);
In the statement a natural join is created on Book and Transaction tables. The
WHERE clause restricts the output of the query.




© SQL Star International Ltd.                                                   174
The USING Clause
Natural joins can be created on tables having columns with same name and same
datatype. However, if tables have columns with same name but different datatype,
the USING clause can be used. The NATURAL JOIN and USING clauses are mutually
exclusive.
The USING clause is used to specify the columns to be used for equijoins. Although
more than one column may match in two tables, the USING clause can be used to
match only one column.
The following statement shows the usage of the USING clause:
SELECT t.cTranID, t.dIssueDt, b.cBookID, b.cBookName,t.dActualReturnDt
FROM Book b JOIN Transaction t
        USING (cBookId)
        WHERE cBookID in
        (‗SFI050001993‘, ‗NFI040000224‘, ‗HUM050001003‘);




The USING clause with WHERE Clause
Use the USING clause with the WHERE clause to restrict records retrieved from two
tables. First, join the tables and then use the USING clause as follows:
        SELECT t.cTranID, t.dIssueDt, cBookID, b.cBookName, t. dActualReturnDt
        FROM Book b JOIN Transaction t
        USING (cBookID)
        WHERE cBookID = ‗FIC030001111‘;
In the above statement, first, the Book and the Transaction tables are joined with
the JOIN keyword using the cBookID column to match the columns. The search is
restricted to condition specified in the WHERE clause.
The ON Clause
A natural join is based on all columns with same name, same datatype, and same
values. You can use the WHERE clause to retrieve the records based on some
condition. You can also specify a condition in the natural joins using the ON clause.
The ON clause specifies a condition that is separate from search condition specified
by the WHERE clause.
The following statement shows the usage of the ON clause:

       SELECT t.cTranID, t.dIssueDt, b.cBookID, b.cBookName,t.dActualReturnDt
       FROM Book b JOIN Transaction t
       ON (b.cBookID = t.cBookID);


© SQL Star International Ltd.                                                    175
In the code you specify the join condition using the ON clause. The Book and the
Transaction tables are joined based on the column cBookID present in both the
tables.
Using ON Clause with Different Column Names
The ON clause can also be used to join tables using columns with different names. It
is similar to a self-join, wherein you join a table with itself. The following statement
shows the usage of the ON clause to create a join using columns with different
names:
        SELECT S.nLibStaffNo StaffNo, S.cLibStaffName StaffName,
      S.nLibMgrNo       MgrNo, M.cLibStaffName MgrName
        FROM LibStaff S JOIN LibStaff M
        ON S.nLibMgrNo = M.nLibStaffNo;
In the statement, the join condition is specified in the ON clause using different
columns.
The query displays the following result:




Creating Three-Way Joins Using ON Clause
In the SQL: 1999 syntax, you can also create three-way joins. That is, you can join
three tables. The join is performed from left to right. The first join is created on the
first two tables. It cannot reference the third table. The second join is created on the
first two tables collectively (created by the first join) and the third table. This way, all
three tables are referenced in the second join.
To retrieve data from the Book, Transaction and Member tables simultaneously,
use three-way join clause in the following manner:

       SELECT m.cMemberID, m.cLastName,
       b.cBookName, b.cAuthorName, t.cTranID,
       t.dIssueDt, t.dReturnDt
       FROM Book b
       JOIN Transaction t
       ON (b.cBookID = t.cBookID)
       JOIN Member m
       ON m.cMemberID = t.cMemberID;

In the query, the first join is created between the Book and the Transaction tables
using the column cBookID. The second join is created between the Book and the
Transaction tables taken together and the Member table using the column
cMemberID. Once the joins are created data can be retrieved simultaneously from
three tables.
OUTER Joins
When you use joins on two tables, it returns all rows that match the condition.
In SQL: 1999 syntax, this type of join is called an inner join.


© SQL Star International Ltd.                                                          176
When a join not only returns the result of an inner join (the matched rows), but also
the unmatched rows, it is called an outer join. The unmatched rows are the ones that
are deficient in information and thus, do not match the condition specified in the join
condition. The information deficiency could be in the right side or the left side of the
join condition. Accordingly, the join is called right outer join or left outer join. If the
deficiency is on both sides of the join condition it is called full outer join.

Left Outer Join
Left outer join enables you to retrieve all rows (matched or unmatched) from the
table specified on the left side of join condition.
To retrieve information about the books that are issued as well as the books that are
not issued to any members, you can give a left outer join query as follows:

       SELECT T.cMemberID, B.cBookName
       FROM Book B
       LEFT OUTER JOIN Transaction T
       ON (B.cBookID = T.cBookID);

The query retrieves the names of the books that are issued to the members.
However, as there is a left outer join on the Book table, the query also retrieves all
books that are not issued to anybody. Book IDs of such books are however not found
in the Transaction Table.
From the output, you can identify member IDs to whom books have been issued.
The books that are available but have never been issued have no match in the
Transaction table and hence no member ID is retrieved along with it. You could get
the same result on issuing the Oracle proprietary syntax as follows:

       SELECT T.cMemberID, B.cBookName
       FROM Book B, Transaction T
       WHERE B.cBookID= T.cBookID(+);

Right Outer Join
Right outer join enables you to retrieve all rows (matched or unmatched) from the
table specified on the right side of join condition. The following statement specifies
right outer join:

       SELECT M.cMemberID, M.cLastName, T.cTranID, T.cBookID, T.dissueDt,
       T.dreturnDt
       FROM Transaction T
       RIGHT OUTER JOIN Member M
       ON (T.cMemberID = M.cMemberID);


The query retrieves the member details and transaction details based on the column
cMemberID. The query specifies right outer join, as there may be a deficiency in
the Member table (on the right side). All members may or may not issue a book
from the library; hence there may not be transaction details for each member.
Full Outer Join
In an outer join, there can be a deficiency on both the sides of the join condition. For
instance, some books may not belong to any category. This is the case when you
buy a new set of books for the library and may not put them in any category for
some time. You just make entries into the Book table, thereby assigning a book ID.
On the other hand, a particular category may not have any books. Such situation can
be handled using full outer joins, wherein both columns specified on either side of
the join condition have some deficiency.
© SQL Star International Ltd.                                                          177
To retrieve information about all books from the Book table (whether or not a book
belongs to a category) and information about all categories (whether or not it
contains any book), you can use a full outer join in the following manner:

      SELECT B.cBookID, B.cBookName, C.cCategoryName
      FROM Book B
      FULL OUTER JOIN Category C
      ON (B.cCategoryID = C.cCategoryID);
You can also give additional conditions with full outer joins
      SELECT B.cBookID, B.cBookName, C.cCategoryName
      FROM Book B
      FULL OUTER JOIN Category C
      ON (B.cCategoryID = C.cCategoryID)
      AND B.cBookID = ‗CLS010009970‘;

Mapping Joins
The Oracle proprietary joins can be mapped to SQL:1999 syntax joins as follows:




SET OPERATORS
You queried multiple tables by joining them using a single query statement. You
could also query multiple tables by joining two individual query statements on the
different tables. This is done using any of these operators:

          o   UNION/UNION ALL
          o   INTERSECTION
          o   MINUS

For instance, to place a requisition for books from your supplier, you need the book
list from two tables. You could:
        Order for all the books in both the tables – a union
        Order for only those books, which are there in both the tables – an
        intersection
        Order for only those books, which are there only in one of the tables - minus
Assume that the New Jersey Central Library maintains two tables, BookArchive and
BookProspect. The former containing details of books that have been stored in the
library for quite sometime and the latter storing information of prospective books
(books they intend to buy). The lists of books in the two tables as seen with a simple
select statement is given below.
        SELECT *
        FROM BookArchive;
        CBOOKNAME
© SQL Star International Ltd.                                                     178
-----------
       Triumph Of Katie Byrne

        Kidnapped
        The Comedy of Errors
        The Magic Faraway Tree
        Oliver Twist
        Woman Of Substance
        The Humor of Humor
        Hamlet
        Wings Of The Storm
        Othello
        10 rows selected.
The list of books in the BookProspect table is:
        CBOOKNAME
        -----------
        Othello
        David Copperfield
        For the New Intellectual
        Hamlet
        Sense and Sensibility
        The Prodigal Daughter
        Oliver Twist
        Honour Among Thieves
        Kidnapped
        The Fountainhead
        10 rows selected.

Union operator
This operator returns the data which are unique to all the tables used in the Query.

The following statement is written, when the library wants to display the list of
archived and prospective books for which he has to place an order.

       SELECT cBookName
       FROM BookArchive
       UNION
       SELECT cBookName
       FROM BookProspect;
The result it displays is:
       CBOOKNAME
       ---------
       David Copperfield
       For the New Intellectual
       Hamlet
       Honour Among Thievesl
       Kidnapped
       Oliver Twist
       Othello
       Sense and Sensibility

© SQL Star International Ltd.                                                     179
The   Comedy of Errors
       The   Fountainhead
       The   Humor of Humor
       The   Magic Faraway Tree
       The   Prodigal Daughter

        Triumph Of Katie Byrne
        Wings Of The Storm
        WomanOf Substance
        16 rows selected.
Using Union operator, all the books contained in the query tables are displayed
eliminating the duplicate once.
However, if you need to display the duplicates data also, you can use the union all
operator.
Intersect operator
This operators returns the data which are common to all the tables used in the
Query.
By using intersect, only those books, which are common to the joined tables, are
displayed. To place an order for those books that are archived and in the prospective
book list issue:
        SELECT cBookName
        FROM BookArchive
        INTERSECT
        SELECT cBookName
        FROM BookProspect;
The result of the statement is:
        CBOOKNAME
        ------------
        Hamlet
        Kidnapped
        Oliver Twist
        Othello


Minus operator
This operators causes the common values to be subtracted from one of the tables
and display the remaining values.
For instance, to place orders for those books that are contained only in the
BookProspect table and not in BookArchive, the following statement is issued:
        SELECT cBookName
        FROM BookProspect
        MINUS
        SELECT cBookName
        FROM BookArchive;
The result of the statement is:
        CBOOKNAME
        ---------
        David Copperfield
        For the New Intellectual
        Honour Among Thievesl

© SQL Star International Ltd.                                                     180
Sense and Sensibility
       The Fountainhead
       The Prodigal Daughter
       6 rows selected.


Guidelines for using the Set Operators


   1. The number and the datatypes of the columns should always match with its
      corresponding query.

   2. The column name in resultant would be based on the outer most SELECT
      statement.




Summary
In this session, you have learnt that:
     Data present in the different tables can be extracted using the JOIN
    functionality in SQL. Cartesian product result when there are no joining clauses in
    the Statement.

    Data can be obtained from multiple tables using Oracle proprietary syntax as
   well as using SQL: 1999 syntax.

      The various Joining options in Oracle proprietary syntax are:

      Equijoin (based on equal value and datatype), Non-Equijoin (based on a
   range of         valid values between the tables), Outer join (to fetch the
   matched as well as      unmatched values) and Self join (to extract information
   from the same table used        in lookup operation)

    In SQL:1999 syntax, along with the above joins, we can also have NATURAL
   Join(based on same column names between the tables), FULL OUTER join
   (deficiency in both the tables) and CARTESIAN join(cross product) respectively.

    Set operators such as UNION (extracts distinct data), UNION ALL (extracts all
   data from both tables), MINUS (uncommon data) and INTERSECT (common data)
   allow us to show data from query based on multiple tables by joining two
   individual query statements.




© SQL Star International Ltd.                                                      181
Lab Exercise
[Note: Questions 1 to 5 are based on Joins using the Oracle syntax. Questions 6 to
10 are based on the SQL 99 Join syntax]

1.     Write a query to retrieve the first name and last name of employees along
with their respective department numbers and department names as shown below.




--------------------
106 rows selected.

2.     Write a query to retrieve the last name, department name, city, and
commission earned of all those employees who earn a commission as shown
below.




3.    Write a query to retrieve the first name, last name, salary and job titles of
      employees belonging to department numbers 100 and 30 as shown below.




© SQL Star International Ltd.                                                  182
12 rows selected.

4.    Write a query to retrieve the employee‘s last names, department numbers,
      and     department names, including those departments that do not have
      employees. The result should be as follows:




          ------------
          122 rows selected.

5.    Write a query to retrieve the names of each employee and their managers.
The   result should be as shown below.




© SQL Star International Ltd.                                             183
--------------------
         106 rows selected.


   6. Write a query to retrieve the last names and department names of employees
      who have superiors. The result should be as shown below.




             -----------------

7.     Write a query to retrieve the names of employees and their managers. The
result should be as shown below.




© SQL Star International Ltd.                                               184
---------------------
          106 rows selected.

8.     Write a query to retrieve the last name, and department name of all
employees    even if the employees have not been assigned to any department. The
result       should be as shown below.




      -----------------
       107 rows selected.

9.     Write a query to retrieve the employee IDs, department numbers, and
department names even if employees have not been appointed to some of the
existing departments. The result should be as shown below.




© SQL Star International Ltd.                                               185
-----------------
     122 rows selected.
10.      Write a query to retrieve the employee ID, department number, and
department names of those employees who have not been assigned to any
department, and those departments to which employees have not yet been assigned.
The result should be as shown below.




© SQL Star International Ltd.                                               186
Chapter 9




                                Understanding Subqueries
    
    
    
                                                     Introduction to Subqueries
                                                            Types of Subqueries
                                                Guidelines for using Subqueries
                                 Single Row Subqueries using group functions
                                Identifying illegal statements with Subqueries
                                                        Multiple Row Subqueries
                                           Multiple Row Comparison Operator
                                     Impact of Null Value on the Outer Query




© SQL Star International Ltd.                                              187
Objectives


At the end of this chapter, you will be able to:

Identify the need for subqueries

Write subqueries




© SQL Star International Ltd.                      188
Introduction to Subqueries
A subquery is a SELECT statement embedded within another SELECT statement. To
understand this, look at a scenario where in you need to find the details of those who
became members after ‗Celena Stevenson‘.

To get the desired result, you would have to frame two queries, one query to find out
the membership date of ‗Celena Stevenson‘ and the other to find out those who
became members after ‗Celena Stevenson‘. By combining these two queries, i.e by
placing one query inside the other you would be able to arrive at the desired result.
The inner query is known as the subquery where as the outer query is called the
main query. The value returned by the subquery is used as the search value in the
main query.
Subqueries are SELECT statements that are part of a clause of another SELECT
statement. Subqueries can be embedded in any of the following SQL clauses:

                        FROM clause
                        WHERE clause
                        HAVING clause
                        ORDER BY clause

The syntax to write a subquery is:

              SELECT select_list
              FROM table
              WHERE <column_name> operator (SELECT select_list
                                    FROM table[WHERE condition]);

In the syntax, operator stands for any comparison operator such as >, =, <>, IN
etc.




Uses of a Subquery
A subquery has the following uses:


      Values can be provided for the conditions specified in the WHERE, HAVING,
           and the START WITH clauses used in the SELECT statements.
© SQL Star International Ltd.                                                     189
A set of rows can be defined and directly inserted into the target table of an
                INSERT or CREATE TABLE statement.

A set of rows can be defined and included in a CREATE VIEW or SNAPSHOT
               statement used for creating views and snapshots .

One or more values can be assigned to existing rows in the UPDATE
               statement.

A table can be defined in a subquery and operations can be performed on it
                by the outer query defined by the INSERT, UPDATE and DELETE
               statements.




Types of Subqueries


The types of subqueries are:

Single-row subqueries :The inner SELECT statement returns only one row.
Multiple-row subqueries:The inner SELECT statement returns more than
                 one row.
 Multiple-column subqueries:The inner SELECT statement returns more
                 than one column.




Using Subqueries

Before using the different types of subqueries, you must remember the guidelines to
be followed while using them.

© SQL Star International Ltd.                                                             190
   Subqueries should be enclosed within parentheses.


     Subqueries should be placed on the right side of the comparison operator.


     Subqueries cannot contain an ORDER BY clause except in a Top-n analysis.
           A main SELECT statement can contain only one ORDER BY clause and it
            must be the last clause.

     There are two types of comparison operators, the single row operators to
            be used with single row subqueries and the multiple row operators to be
            used with multiple row subqueries.



Single-row Subqueries
In single row subqueries the inner SELECT statement returns only one row. Following
single row comparison operators are used in single row subqueries:
        • =
        • >
        • > =
        • <
        • < =
        • < >

‗Tifiny Keener‘, a member of the New Jersey Central Library makes a request to
furnish her with details of all those members who reside in the same area as
hers. But she does not mention the area where she resides. Therefore, to meet
this requirement the desk officer issues the following SELECT statement:

       SELECT cFirstName||cLastName Name,cPhone
       FROM Member
       WHERE cArea = (SELECT cArea
                    FROM Member
                    WHERE cFirstName = ‗Tifiny‘
                    AND cLastName = ‗Keener‘);

The query displays the following result:




Since the library desk officer does not know the area where ‗Tifiny‘ resides, he
issues an inner query to retrieve ‗Tifiny‘s‘ area and then uses the result to
execute the outer query.

© SQL Star International Ltd.                                                      191
The above example had only one condition in the WHERE clause. You can have
multiple conditions too in the WHERE clause.

For example, if you want to know all books written by the author who wrote the
book, which has the ID ‗PSH030000017‘, and which was published after the year the
book having the ID ‗NFI040000224‘ was published, issue the following statement:

       SELECT DISTINCT(cBookName),cAuthorName
       FROM Book
       WHERE cAuthorName = (SELECT cAuthorName
                                          FROM Book
                  WHERE cBookID = ‗PSH030000017‘)
       AND dPublishedYr > (SELECT dPublishedYr
                 FROM Book
                 WHERE cBookID = ‗NFI040000224‘);


The query displays the following result:




Here the query statement contains three queries: the outer query and two inner
queries. First, the two inner queries are executed returning the respective results:
‗Paul Harris‘ and ‗20-JAN-89‘. Then the outer query is executed using the values
returned by the inner query to satisfy its search condition. So the query is to retrieve
all those books written by ‗Paul Harris‘ and which are published after ‗20-JAN-89‘.



Accessing Data from Different Tables
Both the outer query and the inner query can return data from different tables.

For example, based on a query made by a member of the ‗Hamilton‘ branch to
display a list of all those books that belong to the ‗Fiction‘ category, the desk officer
issues the following statement:

       SELECT cBookName,cAuthorName
       FROM Book
       WHERE cCategoryID = (SELECT cCategoryID
                FROM Category
                WHERE cCategoryName = ‗Fiction‘)
       AND cBranchID = ‘03HAMNJ‘;

The query displays the following result:




© SQL Star International Ltd.                                                         192
In this example, the inner query returns the ID of ‗Fiction‘ category from the
Category table. The outer query then is processed using this value to extract the
book details of ‗Hamilton‘ branch from the Book table.



Using Group Functions in Subqueries
You can also use group functions in a subquery. For example, the library
management requests the desk officer to display the details of the junior most
members of the library (according to their age). In order to do so, the desk officer
issues the following statement:

       SELECT cMemberID,cFirstName,cLastName,
       cPhone,nAge,dMembershipDt,cGrade
       FROM Member
       WHERE nAge = (SELECT MIN (nAge)
            FROM Member);


The query displays the following result:




In this example, the inner query uses the MIN function to retrieve the lowest age of
members of the library. The age retrieved is then used as a result for the outer
query.

You can embed subqueries not only in the WHERE clause, but also in the HAVING
clause.

For example, suppose that the library management is interested in knowing about
those books, which are more in stock in the library, than the books written by
‗Charles Dickens‘. To fulfill this requirement the desk officer issues the following
statement:

       SELECT cAuthorName, COUNT (cBookName)
       FROM Book
       GROUP BY cAuthorName
       HAVING COUNT (cBookName)> (SELECT COUNT (cBookName)
                     FROM Book
                                WHERE cAuthorName = ‗Charles Dickens‘);

© SQL Star International Ltd.                                                       193
The query displays the following result:




         6 rows selected.



Multiple-row Subqueries
Examine the query below:

       SELECT cMemberID, nFine
       FROM Transaction
       WHERE nFine = (SELECT MAX (nFine)
                  FROM Transaction
                  GROUP BY dIssueDt);

The query displays an error in the following line:

       WHERE nFine = (SELECT MAX (nFine)
                           *
       ERROR at line 3:
       ORA-01427: single-row subquery returns more than one row

This query attempts to retrieve the IDs of those members who have paid a fine
amount that is equivalent to the maximum amount of fine received on books
borrowed on issue dates taken as a group.

However, on executing this statement the Oracle Server displays an error message
saying, ―single-row subquery returns more than one row‖. This error is encountered
because in the example, the inner query contains the GROUP BY clause, which
causes more than one row to be returned, that is, one result for each group. The
result of the subquery is used in the WHERE clause of the outer query. But the
WHERE clause uses an equal (=) operator, which is a single-row comparison
operator. A single-row operator does not expect more than one value and hence
generates the error.



© SQL Star International Ltd.                                                   194
Therefore, subqueries that return more than one row is called multiple-row
subqueries.

You will have to change single-row comparison operator to multiple-row comparison
operator in order to overcome this error.

Following are the multiple-row operators:




You can modify the example using the multiple-row comparison operator IN as
follows:

       SELECT cMemberID,dIssueDt, nFine
       FROM Transaction
       WHERE nFine IN (SELECT MAX (nFine)
                 FROM Transaction
                 GROUP BY dIssueDt);

The query displays the following result set:




    -------------------
     20 rows selected.



ANY Operator


© SQL Star International Ltd.                                                 195
The ANY operator is used to compare values to each value that a subquery returns
and is used along with =, !=, > and < operators.

On the request of the library management to retrieve the Ids of those members who
have not borrowed books on ‗14-APR-01‘ and have paid a fine amount that is more
than any of the amounts received by way of fines on books issued on ‗14-APR-01‘,
the desk officer issues the following statement:

       SELECT cMemberID,cBookID,
       dIssueDt,nFine
       FROM Transaction
       WHERE nFine > ANY (SELECT nFine
                                FROM Transaction
                                WHERE dIssueDt = ‘14-APR-01')
       AND dIssueDt <> ‘14-APR-01';

The query displays the following rows:




  -------------------
   11 rows selected.

This statement compares the fine amount with the fines received on books issued on
‗14-APR-01‘. Since you have used > ANY, the minimum fine amount received on
‗14-APR-01‘ is $3.

       SELECT nFine
       FROM Transaction
       WHERE dIssueDt = ‘14-APR-01';
       The statement returns:




The outer query then returns those transaction details (other than the transactions of
‗14-APR-01‘) where the fine amount is greater than $3.


© SQL Star International Ltd.                                                     196
ALL Operator

The ALL operator is used to compare a value to every value that a subquery returns.
It is used along with the operators like > and <.

The desk officer issues the following statement to meet the request made by the
management to retrieve those transaction details wherein members have paid fine


amounts exceeding the average amount of fine received on all the dates the books
were borrowed from the library:

       SELECT cMemberID,cBookID,nFine
       FROM Transaction
       WHERE nFine > ALL (SELECT AVG (nFine)
                   FROM Transaction
                   GROUP BY dIssueDt);

no rows selected

This statement compares the fine amount with the average fines received on issue
dates taken as a group.
Executing the subquery below, we get the average of fines.

       SELECT dIssueDt,AVG(nFine)
       FROM Transaction
       GROUP BY dIssueDt;

The query displays the following result set:




     ----------------
     20 rows selected.

Since you have used >ALL, the highest average fine of an issue date is $13.5. The
outer query, however, returns no rows, as there are no members whose fine amount
is greater than $13.5.



Errors in Subquery Statements
© SQL Star International Ltd.                                                   197
When you write subqueries and execute them, you need to be very careful about a
few issues. There may not be any technical or syntactical error but the logic is
executed in such a way that will not get the required result.

Impact of Null Value on the Outer Query

To understand the impact of null values on outer query, look at the statement
written below that displays information about a book, which is not published in the
same year as books written by ‗Enid Blyton‘.

      SELECT cBookName,cAuthorName,dPublishedYr
      FROM Book
      WHERE dPublishedYr NOT IN (SELECT dPublishedYr
           FROM Book
      WHERE cAuthorName = ‗Enid Blyton‘);

This query does not return any rows.

In the above example, you are trying to display those books, not published in the
same year books written by ‗Enid Blyton‘ were published. But, you get a statement
saying no rows selected. This is because one of the values returned by the inner
query is null as the year of publish of one of ‗Enid Blyton‘s‘ book (The Magic Faraway
Tree) is unknown.

You already know that when conditions compare a value to a null value, they result
in null. Therefore, if null values are returned by the inner query, do not use the NOT
IN operator as it is equivalent to ―not all”.

But, if null values are returned by the inner query, you can use the IN operator, as it
is equivalent to ―equal to any‖.

       SELECT DISTINCT(cBookName), cAuthorName, dPublishedYr
       FROM Book
       WHERE dPublishedYr IN (SELECT dPublishedYr
                  FROM Book
       WHERE cAuthorName = ‗Enid Blyton‘);

The query displays the following result set:




© SQL Star International Ltd.                                                      198
By using the IN operator you are trying to display those books, that were published
in the same year as books written by ‗Enid Blyton‘ were published.



Summary

In this chapter, you have learnt that:
    
       Subqueries are used to extract unknown information from a known value.
   These are created by enclosing one SELECT Statement within the other.

    The inner SELECT statement is known as a Subquery and outer SELECT
   statement is known as a Main Query.

    Both the outer query and the inner query can return data from different
   tables.

       Resultant of Outer query is based on the values fetched by the Subquery.

    A subquery can return one or more number of values. Based on the return
   values, comparison operators are divided into single row comparison operators
   (relational operators) and multiple row comparison operators (ALL, ANY and IN).

    Null value generated in a subquery nullifies the entire query resulting in no
   row selected. It can be handled restricting the NULL values using IS NOT NULL
   clause.




© SQL Star International Ltd.                                                      199
Lab Exercise

1.   Write a subquery to display the last name and salary of employees in the
samdepartment as Nancy.




              6 rows selected.


2.   Write a query to retrieve the employee numbers, last names and salaries of all
employees whose salary is greater than the average salary.




           ------------------
          49 rows selected.


3.    Display the last name, department number and salary of all employees whose
location ID is 1400.




© SQL Star International Ltd.                                                   200
4.   Write a query to display the last name, department number, and salaries of all
employees who report to Hunold:




5.   Write a query to display last name, job ID and manager ID of employees
belonging to the marketing department.




            ------------------
           34 rows selected.
6.   Write a query to display the last names, department ID, and salaries of all
employees whose department ID and salary match the department ID and salary of
all employees who earn a commission.




          6 rows selected.




© SQL Star International Ltd.                                                  201
Chapter 10




                                Advanced Subqueries

                                           Multiple column Subqueries
                                Pairwise and Non-Pairwise Comparison
                                         Subquery in the FROM Clause
                                       Working with Scalar Subqueries
                                           Using Correlated subqueries
                                  EXISTS and NON EXISTS operators
                                                          WITH clause




© SQL Star International Ltd.                                     202
Objectives

At the end of this chapter, you will be able to:

       Use Multiple column Subqueries

       Write Subqueries in FROM clause

       Use Correlated subqueries

       Work with EXISTS and NON EXISTS operators

Use     WITH clause




© SQL Star International Ltd.                       203
Multiple Column Subqueries

While using single-row subqueries and multiple-row subqueries, you have only
compared one column in the WHERE clause or the HAVING clause.
But what should be done if the need arises to compare more than one column?

This can be achieved by using multiple-column subqueries, that is, subqueries that
return values for more than one column.

The syntax for writing this subquery is:

       SELECT column, column, …
       FROM table
       WHERE (column, column,…) IN
         (SELECT column, column, …
          FROM table
          WHERE condition);

In a multiple column subquery, the WHERE clause compares columns in two ways:
Pairwise and Non-pairwise. To understand these two column comparison types, let us
look at some examples.



Pairwise Column Comparison

Generate a report with the details of a book whose category ID and number of books
in that category is the same as those of books written by ‗Shakespeare‘. For example
if ‗Shakespeare‘ has written four tragedies, the result should display other authors
who have written four tragedies. The result should not contain details of
‗Shakespeare‘s‘ books.


       SELECT cBranchID,cBookName,
       cAuthorName,cCategoryID,
       nNoOfCopies
       FROM Book
       WHERE (cCategoryID,nNoOfCopies) IN (SELECT cCategoryID, nNoOfCopies
                                FROM Book
                                WHERE cAuthorName=‘Shakespeare‘)
       AND cAuthorName<>‘Shakespeare‘;




© SQL Star International Ltd.                                                    204
The query displays the following result:




-----------------
11 rows selected.

To understand how the pairwise column comparison works, look at the resultant
values obtained by executing the inner query.


       SELECT cCategoryID, nNoOfCopies
       FROM Book
       WHERE cAuthorName= ‗Shakespeare‘;


The inner query displays the following result:




          ------------------------
          10 rows selected.




© SQL Star International Ltd.                                                   205
In pairwise column comparison, each row returned by the outer query must have
both the category Ids and the number of copies same as that for the books written
by ‗Shakespeare‘.




Non-pairwise Column Comparison



Generate a report with details of books whose:

 Category ID is same as any of Shakespeare‘s book category IDs.

  The number of books matches the number of books written by
          ‗Shakespeare‘ in any category.

For example if Shakespeare has written four tragedies and two romances, the result
should also contain details of books of authors who have written either two or four
tragedies or romances.


       SELECT cBranchID,cBookName,
       cAuthorName,cCategoryID,nNoOfCopies
       FROM Book
       WHERE cCategoryID IN (SELECT cCategoryID
                                FROM Book
                                WHERE cAuthorName= ‗Shakespeare‘)
       AND nNoOfCopies IN (SELECT nNoOfCopies

© SQL Star International Ltd.                                                   206
FROM Book
                                WHERE cAuthorName= ‗Shakespeare‘)
        AND cAuthorName <> ‗Shakespeare‘;



The query displays the following result:




------------------
16 rows selected.




© SQL Star International Ltd.                                       207
Subquery in the FROM Clause

So far you have written subqueries in the WHERE clause and the HAVING clause. You
can also embed a subquery in the FROM clause.

The query uses a FROM clause subquery:


       SELECT T.cMemberID, T.cBookID, T.nFine,
       TR.FineAvg, T.dIssueDt
       FROM Transaction T, (SELECT dIssueDt,
                                    AVG(nFine) FineAvg
                                    FROM Transaction
                                 GROUP BY dIssueDt) TR
          WHERE T.dIssueDt = TR.dIssueDt
          AND T.nFine > TR.FineAvg;


The query displays the following result:




© SQL Star International Ltd.                                                208
6 rows selected.

This example displays the member IDs, the book IDs, fine amount, average fines
and the issue dates of those members who have paid a fine amount, which is more
than the average fines paid for that issue date.

In the above statement, the Transaction table is given the alias T and the FROM
clause subquery (which returns value from the Transaction table) is given the alias
TR. This is similar to self-join. The WHERE clause compares the issue dates of the
Transaction table with the issue dates returned by the subquery and also the fine
amount is compared with the average fines for all issue dates that are returned by
the subquery.



Scalar Subqueries

A scalar subquery is a subquery that returns exactly one column value from one row.
It is used to specify a scalar value returned from an expression. You cannot qualify
multiple column subqueries as scalar subqueries.

The value of a scalar subquery expression is the number of rows returned by the
SELECT statement in the scalar subquery. The data type of the return value should
match the value being selected in the subquery.

If the number of rows returned by the scalar subquery expression is zero, the value
of the scalar subquery is NULL. If the number of rows returned by the scalar
subquery is more than one, the Oracle server returns an error. This is because, a
scalar subquery must return exactly one column value from one row.


In Oracle8i, scalar subqueries were supported in the following cases:

SELECT statement (FROM, WHERE clauses)

VALUES list of an INSERT statement




The enhancements made in Oracle9i enable you to use scalar subqueries in all valid
expressions like:

© SQL Star International Ltd.                                                    209
All clauses of a SELECT statement, except the GROUP BY clause
       Conditions and expressions used in CASE and DECODE functions
       The SET clause, on the left hand side of the operator
       The WHERE clause of the UPDATE statement


Scalar subqueries cannot be used in certain cases, such as:

                     Default values for columns
                     The basis for function-based index
                     A returning clause in DML statements
                     In HAVING clauses
                     In GROUP BY clause, CHECK constraints and WHEN condition
                     In Hash expressions for clusters
                     In START WITH and CONNECT BY clauses
                     In statements such as CREATE PROFILE that are not related to
                      queries



A Scalar Subquery in CASE Expression

The following example demonstrates the use of a scalar subquery in CASE
expression. To retrieve the ID and name of all books belonging to the category
‗Fiction‘ in the branch ‗Randolph NJ Library‘, you can use CASE expression in scalar
subquery.


       SELECT cBookID, cBookName,
       (CASE
         WHEN cCategoryID =
          (SELECT cCategoryID FROM Category
           WHERE cCategoryName = ‗Fiction‘)
         THEN ‗Fiction‘ ELSE ‗Others‘ END) Category
         FROM Book
         WHERE cBranchID = ‘04RANNJ‘;




It has an outer query that retrieves the IDs and the names of the books stored in
branch ‗04RANNJ‘ from the Book table. The CASE expression evaluates the category
of the book depending on the result of the inner query. The inner query returns the
category ID of books belonging to the category ‗fiction‘.

When you execute this scalar query, the inner query is executed first. The Oracle
server looks into each row of the Category table and compares the value of

© SQL Star International Ltd.                                                       210
cCategoryName column. If it is ‗Fiction‘, then it returns its category ID to the outer
query. Based on the value of category ID returned, the Oracle server assigns the
value ‗Fiction‘ to category, else assigns ‗Others‘.

The output is:




------------------

38 rows selected.




A Scalar Subquery in ORDER BY Clause

A scalar subquery can be used in ORDER BY clause. To retrieve the ID and names of
books stored in branch ‗01ADLNJ‘ in the order of category, you must issue the
following query:


       SELECT cBookID, cBookName
       FROM Book b
       WHERE cBranchID = ‘01ADLNJ‘
       ORDER BY (SELECT cCategoryName
                 FROM Category c
                 WHERE b.cCategoryID = c. cCategoryID);




The query is sorted based on the category name, which is retrieved by the scalar
subquery that matches the category ID in the Book table with the category ID in the
Category table.

The query retrieves the following output:


© SQL Star International Ltd.                                                     211
--------------------------------
31 rows selected.



A Scalar Subquery in Functions

A scalar subquery can be used as an argument to built-in functions, user-defined
functions and type constructors. For instance, you want to retrieve the book name
and the first three letters of category. You can give a scalar subquery in the SUBSTR
function and retrieve the first three letters of the category. This is shown in the
following code:

       SELECT cBookName,SUBSTR((SELECT cCategoryName
                       FROM Category c
                     WHERE c.cCategoryID = b.cCategoryID)
                     ,1,3)Category
       FROM Book b;

In the code, the inner query is executed first. Matching the category ID from the
Category table and the category ID from the Book table retrieves the category of the
book. As this query is in the SUBSTR function, the letters from position one to three
are only retrieved. Then, the outer query is executed, which retrieves the book name
from the Book table.

The output is shown in the following screenshot:




-----------------
184 rows selected.




© SQL Star International Ltd.                                                    212
Correlated Subqueries


Correlated subqueries are also a type of nested subqueries, but execute differently.
In nested subqueries, the inner query executes first and the resulting value is used
by the outer query. However, in correlated subqueries, the execution is the opposite.
The outer query is executed first and the result is used by the inner query. In other
words, the inner query is driven by outer query. Correlated subqueries are used
whenever every row in a table must be processed and evaluated to generate a
result.

The Oracle server performs a correlated subquery whenever a subquery references a
column from a table specified in the outer query (or the parent statement). A
correlated subquery involves row-by-row processing of the table specified in the
parent statement. These rows are also known as candidate rows. It reads every
candidate row and compares the values in each row against a related data.

Following steps take place when a correlated subquery is executed:

1.   The   candidate row is retrieved (from the outer query or the parent statement)
2.   The   value of the candidate row is used by the inner query
3.   The   result of the inner query is used to qualify or disqualify the candidate row
4.   The   above steps are repeated for all candidate rows

The syntax of a correlated subquery is:


       SELECT column1, column2
       FROM table1 parent
       WHERE column1 operator
                     (SELECT column1, column2
                      FROM table2
                      WHERE expresion1 = parent.expression2);


You can use a correlated subquery to find out all members whose age is greater than
or equal to the average upper age of their grade. Following is the code:


       SELECT cFirstName, nAge, cGrade
© SQL Star International Ltd.                                                         213
FROM Member m
       WHERE nAge >= (SELECT AVG(nUpperAge)
                  FROM MemberFee
                         WHERE cGrade = m.cGrade);


This query uses a correlated subquery where the cGrade column of the table from
outer query is used in the inner query. The inner query calculates the average upper
Age of all members belonging to each grade fetched by the outer query. The inner
query result is used by the outer query. The outer query looks into all records of the
Member table and displays only the records where the age of a member is greater
than or equal to the average upper age of members belonging to a grade. The result
of the query is as follows:




EXISTS Operator in Correlated Subqueries



All types of logical operators can be used with nested subqueries. In addition to
these, you can use the EXISTS operator, which is mostly used with correlated
subqueries.

The EXISTS operator tests whether a row value exists in the resultset of inner query.
If the row value is found in the inner query, the condition is flagged as TRUE, and
the search is discontinued. This holds good for the first occurrence of the row value
in the inner query. If the row value is not found in the inner query, the condition is
flagged as FALSE and the search is continued in the inner query.

If you want to find out the Library staff members who have at least one person
reporting to them, you can use the following correlated subquery with an EXISTS
operator:


       SELECT nLibStaffNo, cLibStaffName
       FROM LibStaff l
       WHERE EXISTS (SELECT ‗x‘
                 FROM LibStaff
                 WHERE nLibMgrNo=l.nLibStaffNo);


On executing the query, the following result is obtained:




© SQL Star International Ltd.                                                       214
In the query, the nLibStaffNo and the cLibStaffName columns of the LibStaff
table are retrieved from the outer query. In the inner query, the search begins from
the first row of the nLibMgrNo column of the LibSatff table. The value in the
nLibMgrNo is matched with the value in the nLibStaffNo column of the LibStaff
table (of the outer query). If a match is found, the condition becomes TRUE and the
result of the outer query is displayed. The EXISTS operator ensures that the search
does not continue further.

Note that in the inner subquery, a constant ‗x‘ is used in the SELECT statement. This
is done for performance reasons. As the EXISTS operator does not return any
specific value but only checks for the existence of a value in a column, it is advisable
to give a constant in the SELECT statement. This is because, having a column name
in the SELECT statement causes a table scan for that column, which affects the
performance.

Alternatively, you can use the IN construct to get the same result as the EXISTS
operator.


       SELECT nLibStaffNo, cLibStaffName
       FROM LibStaff l
       WHERE nLibStaffNo IN (SELECT nLibMgrNo
                         FROM LibStaff
                    WHERE nLibMgrNo IS NOT NULL);




The NOT EXISTS Operator



The NOT EXISTS operator works in a manner opposite to the EXISTS operator. It
checks whether a row value selected in the outer query does not exist in the inner
query and flags a TRUE condition. If it exists, it flags FALSE.

You can use the NOT EXISTS operator to find the categories for which the library has
not stored any books.


       SELECT cCategoryID, cCategoryName
       From Category c
       Where NOT EXISTS (SELECT ‗x‘

© SQL Star International Ltd.                                                       215
FROM Book
                     WHERE
                     CCategoryID=c.cCategoryID);


The query is a correlated subquery. The outer query selects the category ID and the
category name from the Category table. The inner query selects constant value
from the Category table and compares the category ID with the category ID
selected from the outer query. If the two categories match, a FALSE condition is
flagged (as NOT EXISTS operator is used). If the category ID in the inner query does
not match with the category ID in the outer query, the condition becomes TRUE and
the columns from the outer query are returned. Thus, the above code retrieves all
categories that do not have an entry in the Book table, meaning those categories
that do not have any books. The result of the query is as follows:




Alternatively, you can use NOT IN operator in place of NOT EXISTS operator to get
the same result. This is shown in the following example:


       SELECT CategoryID, cCategoryName
       From Category c
       Where cCategoryID NOT IN (SELECT cCategoryID
                         FROM Book);


However, if the result of the inner query contains even a single NULL value, the NOT
EXISTS operator evaluates to FALSE. Therefore, the query will not return any rows
even if the WHERE condition is satisfied.



WITH Clause



In a complex query, it is possible that a query block is used more than once or has
many references. Executing the same query block repeatedly is not advisable from
performance standpoint.

The WITH clause also known as subquery_factoring_clause can be used in such
cases. It:

                     Enables you to use the same query block in a SELECT
                      statement
                     when it is referenced more than once in a complex query
                     Retrieves the results of the query block and stores it in the
                      user‘s
                     temporary table space, thereby improving performance
© SQL Star International Ltd.                                                         216
   Allows you to define a query block before using it in a query
                     Can hold multiple query blocks separated by commas
                     Improves performance, as the calculations in the invoked
                      subquery
                     are done only once
                     Is resolved as in-line view or a temporary table

Using a WITH clause you can improve the readability and maintainability of SQL
statements. It allows you to separate the business logic from data gathering.
Internally the WITH clause is resolved as an in-line view or a temporary table.

You can use a WITH clause to find out the issue dates on which the total fine
collected is greater than the average fine collected. Following is the code:


       WITH TotFinePerIssDt AS (
            SELECT dIssueDt, SUM(nfine) fine_tot
            FROM Transaction
            GROUP BY dIssueDt),


          AvgFinePerIssDt AS (
            SELECT SUM(fine_tot)/count(*) fine_avg
            FROM TotFinePerIssDt)


       SELECT *
       FROM TotFinePerIssDt
       WHERE fine_tot>
          (SELECT fine_avg
           FROM AvgFinePerIssDt)
           ORDER BY dIssueDt;


In the code the WITH clause creates two query blocks TotFinePerIssDt and
AvgFinePerIssDt. The TotFinePerIssDt query block retrieves the total fine
collected on every issue date. The AvgFinePerIssDt query block calculates the
average of the total fine collected on each issue date. To calculate this,
AvgFinePerIssDt query block takes the total fine values from TotFinePerIssDt
query block. Finally, the query retrieves the total fine that is greater than the
average of the total fine collected on each issue date.

Without a WITH clause the query would be very complex, and the use of several
SELECT statements would affect the performance. By using a WITH clause, you can
write a code which is easy to read and maintain. In addition, the results of each
query block is stored in a temporary tablespace and used every time it is referenced,
thereby enhancing the performance.


© SQL Star International Ltd.                                                         217
There are some points you should remember while using a WITH clause. A WITH
clause can:

                     Be used with SELECT statements only

                     Hold more than one query, each of which is separated by a
                      comma.

                     Create a query block, which is available to all WITH element
                      query blocks defined after it and the main query block.

                     Have a query block with the same name as an existing table
                      name, where the query block name is given priority




Summary

In this chapter you have learnt that:

                     Multiple columns in a WHERE clause can be used by writing
                      multiple column subqueries.



© SQL Star International Ltd.                                                        218
   Comparison in multiple column subqueries are done using
                     Pairwise (exact values are searched) and Non-Pairwise
                     (combination of values are searched for) comparisons.

                    Subqueries written in a FROM clause helps us to create a virtual
                     column (non existent column) for calculation purpose. This
                     query is also known as Inline View.

                    Scalar subqueries can be written in a CASE expression, in a
                     Function and in an ORDER BY clause.




© SQL Star International Ltd.                                                      219
Lab Exercise

1.     Write a query to display the last names, department ID and salaries of all
       employees whose department ID and salary match the department ID and
       salary of all employees who earn a commission.




           -----------------

      34 rows selected.


     2. Display the last name, department name and salary of all employees whose
        salary and department name are same as the salary and department name of
        employees located in location ID 1700.




       ----------------

       18 rows selected.
3.      Write a query to display details of employees who have one or more
        colleagues in their department who joined after them, with higher salaries.



© SQL Star International Ltd.                                                  220
------------------

     66 rows selected.


4.     Display the details of employees who are not managers.
       [Hint: Use the NOT EXISTS operator. Also, use the NOT IN operator and see
       the result].




       ----------------

        89 rows selected.




© SQL Star International Ltd.                                               221
Chapter 11




                                          Data Manipulation

                                      Various types of INSERT statements
                                               Create UPDATE statements
                                            Generate DELETE statements
                          Single set Aggregate in DML RETURNING Clause
                       Transaction command to Save and discard changes
                                                       Locking Mechanism
                                       Show how Read consistency works




© SQL Star International Ltd.                                       222
Objectives



At the end of this chapter, you will be able to:


    Describe the Data Manipulation Language

    Perform 10g Single Set Aggregates in DML

    Control the Database Transaction




© SQL Star International Ltd.                      223
Manipulating Data
In the previous sessions, the library database users have only extracted the data
stored in the database. For instance, when a member wishes to see a list of all the
books stored in the library, the desk officer issued a simple SELECT statement as
follows:


        SELECT *
        FROM Book;


However, when the desk officer issues the same statement after a few days, he may
observe some noticeable variations in the resultant output. For instance, there would
be additions to the already existing list of books, or a particular book may no longer
be stocked. This reflects that the data stored in the database is dynamic in nature.

These changes involve:

    Adding new data
    Modifying existing data
    Removing data

This chapter deals with how a database developer should implement these changes.
These changes are made possible by the use of Data Manipulation Language (DML).
The following DML statements are executed in order to manipulate the data in the
database:

      INSERT
      UPDATE
      DELETE
      MERGE




Insert Rows

In every organization, the new data or additional data must necessarily be
incorporated into the database. For example, when people enroll themselves as
members of the New Jersey Central Library, their details must be added to the
Member table. Similarly, details regarding new books ordered by the library should
be inserted into the Book table. In order to add new data to the tables, use the
INSERT statement. Its syntax is:


        INSERT INTO table [(column [, column…])]
        VALUES(value [, value…]);


© SQL Star International Ltd.                                                     224
N.B.: [This is not a complete syntax.]




Where,
table is the name of the table into which new column values are inserted.

(column [, column…]) are the columns of the specified table into which the values
are inserted.

(value [, value…]) these are the actual values that are inserted into the columns
specified.

There are different ways of inserting data into a table using the above syntax.



Ways of Inserting Data
The Oracle server enables you to insert data into the database in the following four
ways:

      Inserting   values   for each column
      Inserting   values   for selected columns
      Inserting   values   using substitution variables
      Inserting   values   from another table



Inserting a Row Containing Values for Each Column
Suppose the library has ordered for a ‗Paul Scott‘ book. When the book is delivered,
the librarian has to enter the relevant information into the Book table. To do so, the
following INSERT statement should be issued:


        INSERT INTO Book (cBookID,cBookName,cAuthorName,
        cCategoryID,cPublisherID,
        dPublishedYr,cBranchID,
        nNoOfCopies)
        VALUES (‗FIC011111111‘,‘Jewel In The
        Crown‘, ‗Paul Scott‘,‘01FIC‘,‘HC0176',‘25-NOV-1966', ‘01ADLNJ‘, 2);


    1 row created.

The INSERT statement tends to become quite cumbersome, especially when all the
details of a book must be added. To resolve this issue, Oracle makes it optional to
specify the column list in the INSERT clause, if a row being inserted contains values
for each column.

© SQL Star International Ltd.                                                      225
INSERT INTO Book
       VALUES (‗FIC011111111‘,‘Jewel In The Crown‘, ‗Paul
       Scott‘,‘01FIC‘,‘HC0176',‘25-NOV-1966',‘01ADLNJ‘, 2);


       1 row created.

But, in the above statement how would you know what data will be inserted into
which column? This is achieved by listing values in the VALUES clause according to
the position of columns in the table.

In order to determine the default order of the columns in the table, use the
iSQL*Plus DESCRIBE command.

For example to view the structure of the table Book, use the following code:

       DESCRIBE Book

While using the INSERT statement, you need to remember the following points:

Enclose character and date values in the VALUES clause within single quotation
        marks.
 You can also insert pseudo columns such as SYSDATE, USER (displaying the
        current users name) and conversion functions.



Inserting Rows that Contain Values Only for
Some Columns

In the above example, on the arrival of the new book, the entire details are inserted
into the Book table using the INSERT statement. However, at times the library may
not have all the details of a new book. For instance, on the delivery of a new book
‗Roots‘, the library did not have details of its publisher. In such a case, only the
available details are inserted and the remaining columns are left null, so that they
can be inserted later.

To insert null values, the Oracle server provides two methods:

    Implicit Method
    Explicit Method



Implicit Method


© SQL Star International Ltd.                                                      226
In this method, you can omit those columns from the column list, into which values
are not to be inserted. The following INSERT statement specifies only those columns
into which values are to be inserted:




       INSERT INTO Book (cBookID, cBookName,
       CAuthorName, cCategoryID, cBranchID)
       VALUES (‗FIC051111112‘,‘Roots‘,‘ALEX HUXELY‘,‘01FIC‘,‘05PRINJ‘);


Ensure that these columns allow null values. You can verify this using the iSQL*PLUS
DESCRIBE command.



Explicit Method

In this method, specify the NULL keyword in the values list for those columns into
which values are not to be inserted. The above INSERT statement could be rewritten
as follows:


       INSERT INTO Book
       VALUES (‗FIC051111112‘,‘Roots‘,‘ALEX
       HUXELY‘,‘01FIC‘,NULL,NULL,‘05PRINJ‘,NULL);
This statement omits the column list in the INSERT clause. In the VALUES clause, the
NULL keyword is specified in place of all those columns whose values are not known.



Inserting Rows Using Substitution Variables
Till now you have inserted only single rows into a table. However, in reality you
would be required to insert multiple rows.

For instance, a library would always place a bulk order for books. In such a scenario,
you can imagine how tedious it would be to issue that many INSERT statements.
This can be made easier if the user is prompted to enter the new values each time.

This is achieved by using the iSQL*PLUS substitution variables. You can insert details
of a bulk order of books delivered using substitution variables as follows:


       INSERT INTO Book (cBookID, cBookName, cAuthorName, cCategoryID,
       cPublisherID, dPublishedYr, cBranchID, nNoOfCopies)
       VALUES (‗&BkID‘, ‗&BkName‘, ‗&Author‘, ‗&CatgID‘,‘&PubID‘, ‗&PubYr‘,
       ‗&BrnID‘, &Copies);




© SQL Star International Ltd.                                                     227
Inserting Rows from Another Table
The New Jersey Central Library maintains an IncompleteTransaction table to store
details of those transactions where members have not returned the borrowed books
for more than six months. Instead of inserting these details manually, Oracle
provides an option of populating the table with values derived from an existing table,
which in this case is the Transaction



table. This is achieved by using a subquery instead of the VALUES clause in the
INSERT statement.

Its syntax is as follows:


               INSERT INTO table [column (, column)]
               subquery;


Remember that the number of columns and their datatypes specified in the column
list must be the same as the number of columns and their datatypes specified in the
subquery.

The following example illustrates how the usage of the subquery in the INSERT
statement populate the IncompleteTransaction table.


       INSERT INTO IncompleteTransaction
       SELECT cTranID, cMemberID, cBookID, dIssueDt, dReturnDt,
       dActualReturnDt, nFine
       FROM Transaction
       WHERE dActualReturnDt IS NULL
       AND (SYSDATE-dIssueDt) > 185;


       2 rows created.

You can view the values inserted into the IncompleteTransaction table.


       SELECT *
       FROM IncompleteTransaction;


Displays:

CTRANID      CMEMBERID   CBOOKID          DISSUEDT DRETURNDT DACTUALRE
NFINE
------- --------- ------  ------- -------- --------- -----
T0000300100 CBW109702 ROM020003211 07-SEP-00 21-SEP-00

© SQL Star International Ltd.                                                     228
T0000241000 CRB038901 PSH010000010 11-OCT-00 25-OCT-00




Update Data
Just as you enter details of new members in the Member table, similarly any change
in the members‘ information, such as their address, requires you to incorporate
these changes effectively in the database tables. Such changes in the existing data
are made using the UPDATE statement.

The syntax for using the UPDATE statement is:


       UPDATE table
       SET column = value [, column = value,…]
       [WHERE condition];
Where,
table is the name of the table you are attempting to update.
column is the column in the specified table whose value is to be updated.
value is the new value with which the old column value is to be replaced.
condition specifies the condition for the rows to be updated



Variations in Updating Data
Oracle provides different ways in which you can update the data in a database table.
These are:

    Updating Specific or all the Rows
    Updating Using Subqueries
    Updating Rows Using Values from Other Tables



Updating Specific or all the Rows
In order to update specific row(s), you must specify the WHERE clause in the
UPDATE statement.

For example, a library member Jessica Hatcher has intimated the change in her
address and phone number. In order to incorporate these changes the following
UPDATE statement is to be issued:
       UPDATE Member
       SET vAddress = ‗112, Rockturn Manor Apts.Second Cross Rd‘,
       cPhone = ‗9678111903‘


© SQL Star International Ltd.                                                   229
WHERE cFirstName = ‗Jessica‘
       AND cLastName = ‗Hatcher‘;
       1 row updated.



In this example if the WHERE clause had been omitted, all the members‘ address and
phone numbers would have been updated.

However, it is advisable to use the primary key column in order to update a specific
row. This is due to the using of non-primary key columns (such as cFirstName and
cLastName) that may cause other rows to be updated too. For instance in the
above example, you used the member name to identify the specific row that is to be
updated. It works fine as long as there is only one member with the name Jessica
Hatcher. But it could cause a problem if the library has more than one member with
the same name.



Updating Using Subqueries
In order to update column values for specific rows with already existing values of the
table you can use subqueries in the SET clause of the UPDATE statement.

For example, suppose the ‗Dorrance‘ publishing company shifts its company location
to the same area as that of the Blackwell publishing company, then you need to
update ‗Dorrance‘ publishing company‘s address to that of Blackwell publishing
company‘s address. This can be achieved using subquery in the UPDATE statement.
We will First have a look at its syntax:


       UPDATE table
       SET (column, column,…) =
                   (SELECT column, column,…
                    FROM table WHERE condition)
       WHERE condition;


The syntax is same as an UPDATE statement, except that the SET clause contains
columns whose values are updated using values retrieved from subqueries.


Now use this syntax to update the above-mentioned change in the PublisherDetails
table.


       UPDATE PublisherDetails
       SET vPublisherAddress= (SELECT
                           vPublisherAddress

© SQL Star International Ltd.                                                     230
FROM PublisherDetails




                                    WHERE cPublisherName= ‗Blackwell‘)
       WHERE cPublisherName=‘Dorrance‘;
       1 row updated.




Updating Rows Using Values   from Other Tables
Just as you can populate a table using values from an existing table, similarly you
can update rows by using subqueries that return values from other tables.

For example, suppose the New Jersey Central Library creates a table, RandolphBks
having a structure similar to the Book table and populated with details of books
stored only in the ‗Randolph NJ Library‘.

The library management may decide to update the number of copies of books stored
in the above created table with the number of copies of book number
‗MYS010000001‘ from the Book table as follows:


       UPDATE RandolphBks
       SET nNoOfCopies = (SELECT nNoOfCopies
                    FROM Book
                    WHERE cBookID=‘MYS010000001');
       38 rows updated.




Using Explicit Default Values

In Oracle9i, enhancements were introduced with regard to the usage of the DEFAULT
keyword. Whenever the DEFAULT keyword is used, the default value specific to the
column is applied. This is a feature of the SQL: 1999 standard. The benefit of using
this feature is that, data integrity is ensured, and you need not hard code literals in
your applications.

You can specify a default value for the columns. Later, whenever you use the
DEFAULT keyword, the default value is taken for that column. If you do not specify a
default value for a column, then the Oracle server sets the column to null. Explicit
DEFAULT can be used in INSERT and UPDATE statements.

For instance, when the New Jersey Central Library procures a new set of books,
entry for the new books is made in the Book table. Initially you may not decide upon
© SQL Star International Ltd.                                                      231
the categories to which the books belong. Therefore, you put them in a common
category. Under such circumstances, you can set the default value for the category
ID in the Book table and make entries. Here, the default value is set as ‗01HUM‘.
First, alter the Book table to modify the category column to take the default value as
‗01HUM‘.

       ALTER TABLE BOOK
       MODIFY cCategoryID DEFAULT ‘01HUM‘;

Now, you can make new entries in the Book table as follows:

INSERT INTO Book(cBookID, cBookName, cCategoryID, cPublisherID, cBranchID)
VALUES (‗XYZ0135599555‘,‘Fish‘, default, ‗PN0135‘, ‗01ADLNJ‘);

When you execute this query, book details are entered into the Book table.
However, for the category of the book, the default value is entered.




You can also use the DEFAULT keyword in UPDATE statements to set default values
for the columns. In the following query we will change the category ID of the book
‗Fun With Maths and Physics‘ to the default value of category ID, that is, ‗01HUM‘.


       UPDATE Book
       SET cCategoryID=DEFAULT
       WHERE cBookName=‘Fun With Maths and Physics‘;




Delete Data
© SQL Star International Ltd.                                                     232
The purpose of creating a database and maintaining it is to ensure that it truly
reflects the changes taking place in the real world. For instance, if library member
Nina Philip terminates her membership with the library, retaining her details in the
Member table does not serve any purpose. You can remove any such unnecessary
data using the DELETE statement. Its syntax is:


       DELETE [FROM] table
       [WHERE condition];


The DELETE statement removes the entire rows unlike the INSERT and UPDATE
statements, which allow the adding of values to specific columns or updating only
specific column values. In order to delete specific column values, set their values to
null using the UPDATE statement. Since the WHERE clause is optional, omitting it will
cause all the rows to be deleted.



Ways of Deleting Rows
There are two ways of deleting data from tables. These include removing:

    All or specified data
    Data using subqueries



Removing Specific Rows or All Rows
By specifying the WHERE clause you can delete specific row or rows. For instance,
the New Jersey Central Library maintains a NonMember table, wherein the details
of ex-members are stored. Their details are used to communicate any new schemes
the library comes up with. However, the details of those non-members are deleted
who fail to respond to any correspondence sent to them.


DELETE FROM NonMember
WHERE cFirstName = ‗Susan‘
AND cLastName = ‗Philip‘;


1 row deleted.




© SQL Star International Ltd.                                                     233
Deleting Rows Using Subqueries
Similar to inserting and updating rows using subqueries, you can delete rows from a
table by using values returned by the subquery, written in the WHERE clause.

For example, due to lack of response to any of the correspondence made by the
library to non-members of the Hamilton NJ Library branch, the management decides
to delete their details from the NonMember table as follows:


      DELETE FROM NonMember
      WHERE cBranchID = (SELECT cBranchID
                           FROM Branch
                    WHERE cBranchName = ‗Hamilton NJ Library‘)


      2 rows deleted.



In this example, the subquery returns the branch ID of Hamilton branch. This value
is then used in the WHERE clause of the DELETE statement.




© SQL Star International Ltd.                                                  234
Single set aggregates in DML RETURNING clause

         Oracle10g Offers new enhancements that allow the use of single-set aggregate
            functions in the returning clause of the DML statements. This can result in
            significant performance gains in transactions that process many rows of the
            same table - such as in batch processes.

The DML statements that can use the single-set aggregates in their returning clauses
are INSERT, UPDATE and DELETE. We will begin with the INSERT statement.

Single-set Aggregates in the INSERT Statement

The general format for the INSERT statement when using a RETURNING clause for a
single table insert, using the INTO clause is shown below.


         INSERT INTO <table or expression> <alias> (column,?)
         <values_clause>|<subquery>
         RETURNING <exprs> INTO <data_items>;

Where,

table or expression is a valid table, materialized view, single-table view, or an
expression based on one of the above.

alias is a valid alias for the table or expression.

Column is a comma-separated list of column names or a single column name.

Values clause is a valid values clause to be used to provide inserted values.

Subquery is a valid subquery to generate inserted values

exprs is a set of expressions based on the affected row

data_items is a valid set of variables into which values are returned by the
expressions

Single-set Aggregates in the UPDATE Statement
When the target of the UPDATE is a single row, the RETURNING clause can retrieve
column expressions using the affected row, rowid, and REFs to the affected row.
Single-set aggregates can only be used when the returning clause returns a single
row. These aggregates cannot be combined with simple expressions in the same
returning clause.




© SQL Star International Ltd.                                                       235
An example of UPDATE using the RETURNING clause and a single-set aggregate is
shown below.

        SQL> VARIABLE Total_Fine NUMBER
    SQL> UPDATE Transaction
       SET nfine=nfine*0.5
       RETURNING SUM(nfine) INTO :Total_Fine;
    SQL> PRINT Total_Fine


Single-set Aggregates in the DELETE Statement

The general format for the DELETE statement when using a RETURING clause for a
single table delete is shown below.
       DELETE <table or expression> <alias>
       WHERE <where_clause>
       RETURNING <exprs> INTO <data_items>;


Transactions


Transaction, in simple words is a series of data manipulation statements executed as
one logical unit of work.

But, why are DML statements executed as one logical unit of work?
This could be understood by looking at the outcome of treating data manipulating
statements as individual activities.

An act of a customer purchasing a product of certain quantity, is a transaction, which
comprises of two different activities:

   
    Updating the stock level of the product in Product table
    Entering the cash received details in the CashTransaction table.


But, after making the payment if the customer decides to change the quantity of the
product purchased, then Oracle would not be able to undo the stock level updates or
© SQL Star International Ltd.                                                     236
the cash received at entry, as these two activities have been saved to the Oracle
database individually. Hence, the changes will not be reflected in the respective
tables. This is because we have treated them as two individual activities independent
of each other.

But in reality when a product is purchased both the activities involved are performed
simultaneously.

Therefore, a collection of DML statements is executed as a single unit of work, which
is a transaction.

The act of purchasing a product affects more than one table. However, if you wanted
to reverse the transaction would it get reflected in all the required tables?

Controlling your transactions can solve this problem.

The different types of transactions are:
    DML transactions that comprise any number of DML statements treated as
       one unit of work
    DDL (Data definition language) transactions that comprise only one DDL
       statement
    DCL (Data control language) transactions that comprise only one DCL
       statement



Controlling Transactions

You can control transactions using transaction control mechanisms. Transaction
control mechanism comprises of a set of commands that define the beginning, end
and breakpoint of a transaction.

These commands are called transaction control commands and are as follows:

    COMMIT permanently saves the data changes
    ROLLBACK discards all data changes
    SAVEPOINT divides a transaction into different sections



Using Transaction Control Commands


There are two ways to control transactions, which are:

    Explicit transaction control
    Implicit transaction control



Explicit transaction control
© SQL Star International Ltd.                                                     237
To control the transactions explicitly you need to use the COMMIT, ROLLBACK and
SAVEPOINT control statements. Each of these is explained below .



COMMIT
The COMMIT statement is issued when the user is satisfied with all the changes
made and therefore is ready to save them to the database. Issuing a COMMIT
statement ends the current transaction and begins a new one.

For example, the following DML statement is issued on the Member table to update
the phone number of Stanley Davenport:


      UPDATE Member
      SET cPhone=‘9865457989'
      WHERE cFirstName=‘Stanley‘
      AND cLastName=‘Davenport‘;


      1 row updated.

But before issuing a COMMIT statement the state of data in the Member table would
be as follows:

    Other users cannot change all those rows that are currently being changed by
      another user. This is known as the locking of rows.
    Changes made to the data get reflected only in the SQL buffer and not in the
      database. Therefore the previous state of the data can be recovered if you
      want to discard the changes made.
    The current user can view the result of the DML statements, by using the
      SELECT statement. But other users cannot view the changes, as the changes
      have not yet been permanently saved to the database.


      SELECT cPhone
      FROM Member
      WHERE cFirstName=‘Stanley‘
      AND cLastName=‘Davenport‘;




      CPHONE
      ----------
      9865457989


But after issuing a COMMIT statement as follows:

© SQL Star International Ltd.                                                 238
COMMIT;
       Commit complete.


    Changes to the data are made permanent in the database, hence, the
      previous state of the data cannot be recovered.
    All users can view the result of the DML operations as the changes are
      permanently saved to the database.
    Other users can now perform new data changes as the locks on the rows are
      released.



ROLLBACK


The ROLLBACK statement is issued when the user wants to discard changes made to
the data before they are committed and made permanent. If the user deletes rows
that should not be deleted, the deletion could be undone by issuing the ROLLBACK
statement. For example, you may accidentally delete all the rows from the
Transaction table while attempting to delete only one record from the table.

       DELETE FROM Transaction;

       32 rows deleted.

Issuing the ROLLBACK keyword and then writing the correct transaction can undo
this.


       ROLLBACK;
       Rollback complete.


       DELETE FROM Transaction
       WHERE dIssueDt=‘05-MAY-2001';
       2 rows deleted.


       COMMIT;
       Commit complete.


ROLLBACK statement not only undoes the current transaction, but also marks the
beginning of a new one.

State of the data before ROLLBACK is similar to that before COMMIT. But after
ROLLBACK,
   
© SQL Star International Ltd.                                               239
 All changes to data are undone.
    Previous state of the data is recovered. In the example you can check the
      status by issuing a SELECT statement for the Transaction table library
      database.
    Other users can perform new changes to data as the locks on the rows are
      released.

During the execution of a transaction, if a DML statement fails, only its effect is
rolled back. But all the other data changes made by the previous DML operations are
not scraped away. This kind of functionality is performed implicitly.
For example, while attempting to delete Shakespeare‘s book details from the Book
table, the following error message is displayed and the effect of the DML operation is
rolled back implicitly:

       DELETE FROM BOOK
       WHERE cAuthorName=‘Shakespeare‘;
       DELETE FROM BOOK
       *
       ERROR at line 1:
       ORA-02292: integrity constraint (SCOTT.TRANSACTIONBOOKIDFK) violated –
       child record found


You receive the child record found violation error because you have attempted to
delete ‗Shakespeare‘ books from the Book table, which are being referenced in the
Transaction table. Such errors are known as Integrity Constraint Errors and are
covered in depth in the subsequent chapters.



SAVEPOINT


Issuing a ROLLBACK statement ends the current transaction by discarding all the
changes made to the data. But, a user may not always want to discard all the
changes made, simply because the last statement issued contains changes which are
unwanted. Therefore, divide the transaction into different segments so that you can
discard those segments you want to while keeping the rest intact. The syntax to use
SAVEPOINT is:

       SAVEPOINT name;


For instance assume that you have executed the following transaction in the library
database:


       INSERT INTO Transaction
       VALUES (‗T000300501‘,‘BJH029405',
       ‗MYS010000065‘,‘11-MAY-2001',‘25-MAY-2001'

© SQL Star International Ltd.                                                     240
,NULL,NULL);
       1 row created.


       SAVEPOINT InsertTran;
       Savepoint created.


       UPDATE Transaction
       SET dActualReturnDt= ‘27-MAY-2001'
       WHERE cTranID=‘T000300501';
       1 row updated.


       SAVEPOINT UpdateTran;
       Savepoint created.

       DELETE FROM Transaction
       WHERE cTranID=‘T000300501';

       1 row deleted.

In the example, the transaction has been divided into small sections by using the
SAVEPOINT statement.

In case you want to rollback any of these transactions, then you will have to issue
the ROLLBACK TO SAVEPOINT clause, which rolls back the current transaction to the
specified savepoint. So, all the changes made after the savepoint are discarded. If
this clause were omitted, the ROLLBACK statement would discard the entire
transaction. Hence, to rollback the transactions to a particular point only, add the
following statement:

       ROLLBACK TO UpdateTran;

       Rollback complete.

In the example, the ROLLBACK TO UpdateTran clause rolls back the deletion made
after the issue of the savepoint UpdateTran, while keeping the insertion and
updation, made prior to the savepoint, intact.



When Does a Transaction begin   and end?
A transaction begins when the Oracle server encounters the first executable SQL
statement written by the user on logging on to the SQL*PLUS environment. The SQL
statement could be DML, DDL or DCL statement.

A transaction ends on the occurrence of the following:
© SQL Star International Ltd.                                                   241
 Saving or committing
     Execution of a DDL or DCL statement because they automatically save the
       activities performed
     A user exiting from the SQL*PLUS environment.
     Machine failure

When one transaction ends, the next transaction begins with the next executable
SQL statement.



Implicit Transaction Control

Implicit transaction controls do not involve the use of transaction control commands. Instead, the
functionality of these commands automatically occurs under different circumstances.


Automatic Commit

Under the following circumstances, an automatic commit occurs:

     Issue of a DDL or a DCL statement, or
     Normal exit from SQL*PLUS environment, or
     Keeping the SQL*PLUS, AUTOCOMMIT command on. Therefore, as soon as
       each DML statement is executed, it is committed. Hence, they cannot be
       rolled back.


Automatic Rollback

An automatic rollback occurs when the user exits from SQL*PLUS environment
abruptly, i.e. shutting down the machine without following the normal exit routine or
if the system crashes. In either case the entire transaction is rolled back and the
initial state of the data, as it was at the time of the last commit, is returned. This
prevents unwanted changes to be made to the data.




© SQL Star International Ltd.                                                                242
Locking Mechanism
Different users access the database to perform different operations. Database users
accessing the database perform the following two types of operations:

    Read operations to retrieve data from the database but not make any
      modifications to it (SELECT statement)
    Write operations to perform modifications to the data in the database
      (INSERT, UPDATE, DELETE statements)

Therefore it is necessary to ensure that the users reading from and writing to the
database get a consistent view of the data at all times. This is referred to as read
write consistency.

Read consistency is needed to ensure that,

    Both, the database reader as well as the writer gets a consistent view of the
      data.
    Readers get to see the data that is not in the process of being changed.
    A change made by one writer does not conflict with changes made by another
      writer.

The tool used to achieve this is locking. In order to prevent data from being modified
by more than one user, the Oracle server uses the locking mechanism, which
requires no user effort. It is fully automatic and occurs for all SQL statements except
SELECT.

Locks are broadly classified into two types namely:



1. DML Locks Or Data Locks

      Table level Locks
       Row level Locks

2. DDL Locks

What Happens when Row-Level Lock is placed on Row?

First a DML Lock is placed on the row.

    No Other Transaction Can Lock Or Update this Row

    This Lock will be released when the locking transaction commits or rollback.

Secondly, a DDL Lock is placed on the table, containing the row, to prevent anyone
from altering or dropping the table while the row is undergoing the update.

What happens when a Table level Lock is placed on the table?


© SQL Star International Ltd.                                                          243
 Only the table Locking Transaction can Update Rows in the table

    No rows in the table can be updated by other transactions


      The whole table is Locked

    Other Transaction can query the table, including the one being updated in the
       table - Writers won‘t block Readers.

    Transactions that query the table will be redirected to the rollback data to
       satisfy the query.




The following example illustrates the locking mechanism.

‗Lisa Carmen‘ attempts to update the number of copies of the book ‗Fractals
Everywhere‘ in the Book table. The Oracle server keeps a copy of the data before it
is updated into a segment within the server known as the rollback segment.

Before she commits the change she will be able to view the modifications made to
the data. But all other users will see only the copy kept in the rollback segment.
Therefore, when user ‗Matt Scummen‘ attempts to read data from the Book table,
he will get the data that is kept in the rollback segment. This ensures that the
database readers get data that is not currently being modified.

After ‗Lisa Carmen‘ commits the DML operation, the change is made permanent to
the database. It now becomes visible to anyone attempting to execute a SELECT
statement. So, now when ‗Matt Scummen‘ issues a SELECT statement he gets the
new updated data. The space that was occupied by the old data in the rollback
segment is released so that it can be reused.

Instead, if ‗Lisa Carmen‘ decides to rollback the DML operation, the Oracle server
writes the data kept in the rollback segment back to the table. Therefore, all the
users are able to see the data as it existed before the transaction began.

Read Consistency
Consider 2 users using the same table for two different operations as shown in the
table below.



© SQL Star International Ltd.                                                  244
When user2 queries the Member table after some time he gets the old telephone no
(9865457989) till the time user1 commits.




Summary


In this chapter, you have learnt that:

      Data within the database can be manipulated using the Data Manipulation
        command (DML).

       The various DML commands are,

© SQL Star International Ltd.                                                 245
INSERT: Adding new values into table, UPDATE: modifying the existing
         values DELETE: removing the values and MERGE: adding and modifying
         data based on the condition in a single statement.
       These DML commands can be made interactive using the substitution
         variables (‗&‘) in the scripts.
       RETURNING INTO clause can be used in DML statement to view
         modifications done by the DML operation. This feature avoids using another
         SELECT statement to see the changed value.
      Transaction can either be saved or undone using Data Transaction Control
         Statement. COMMIT statements make the transaction permanent and
         ROLLBACK statement reverses all the un-committed transaction.
      Rows in a table undergoing a change, gets implicitly locked. Explicit locks can
       also be applied on the tables.
      Only committed data is viewed by all the users. This is known as read
         consistency.




© SQL Star International Ltd.                                                     246
Lab Exercise
[Note: For questions 1 to 8, you are required to insert, update and delete data from
the OfficeStaff table.]

To work with the OfficeStaff table, run the LabEx11_00.sql script file. This creates
the OfficeStaff table. The structure of the table is as follows:




The rows to be inserted are given below.




1.   From the sample data given above, insert the first row into the OfficeStaff
     table without listing the columns in the INSERT clause.

© SQL Star International Ltd.                                                   247
2.   Insert the second row from the sample data into the OfficeStaff table by
     explicitly listing the columns in the INSERT clause. Confirm the creation of
     rows.

3.   Create a script file LabEx11_03.sql. Within the file write an INSERT statement
     to populate the OfficeStaff table. The INSERT statement should be such that it
     prompts you to enter the required values. To produce values for the Mail_ID
     column, concatenate the first letter of first name with the last names.

4.   Now run the script file to insert the next two rows of sample data. Make the
     data inserted permanent. Confirm the rows inserted into the OfficeStaff table.

5.   Increase ‗Susan Bright‘s‘ salary by 10%.

6.   Remove the details of ‗Morgan Sheen‘ from the OfficeStaff table. Confirm the
     changes made. Commit the changes made.

7.   Insert the last row of the sample data. Mark a savepoint immediately after
     inserting the row.

8.   Delete all the rows from the OfficeStaff table. Confirm that the table is empty.
     Now,rollback the DELETE statement, but ensure that the earlier INSERT
     statement is not discarded. Make the transaction permanent.

9.   Write a query to update the salary of the employees working in department
     number 10 by 10% and using the returning clause to print the updated value.




© SQL Star International Ltd.                                                    248
Chapter 12




                                       Managing Tables

                                          Data Definition Language
                                Datatypes used in Defining columns
                                                   Modifying Table
                                                          Structure
                                      Manipulating Table Definition
                                                   Flashback Table




© SQL Star International Ltd.                                  249
Objectives

At the end of this chapter, you will be able to:

 Create tables

 Identify the datatypes used when defining the columns

 Modify table structure

 Understand Flashback table




© SQL Star International Ltd.                               250
Introduction
In order to store data in an organized manner, Oracle provides data containers
known as Database Objects. Oracle also provides a mechanism by which you can
create and manipulate them. To understand the creation of database objects, you
must first know the different types of database objects.


Database Objects
Any data structure created within the database for a specific purpose is known as a
database object. Oracle provides various database objects, which are as follows:

Table for storing data

View for providing a customized view of data from one or more tables

Sequence for generating numeric column values that serve as primary keys

Index to retrieve data faster from the database

Synonym to give alternative names to other database objects

In order to create the above listed database objects, you must use a language that
supports database object creation. The language provided by SQL for database
object creation, modification and removal is the Data Definition Language or DDL.


Data Definition Language
Data Definition Language (DDL) comprises of a set of SQL commands that are used
to:
   Create database objects
   Alter database objects
   Drop database objects
   Truncate rows with the database objects
    Rename the database objects

The DDL commands that perform the above-mentioned tasks are:
   CREATE
   ALTER
   TRUNCATE
   DROP
    RENAME




© SQL Star International Ltd.                                                     251
Creating Tables
A table is a database object that stores data. Here, the data is stored in the form of
rows and columns. Each row consists of one or more columns. The DDL statement
used to create a table in the database is CREATE TABLE.

CREATE TABLE Statement

To create a table with the CREATE TABLE statement, the syntax is as follows:


         CREATE [GLOBAL TEMPORARY] TABLE [schema.] <table_name>
         (Column datatype [DEFAULT expr] [,….] );

Where,

GLOBAL TEMPORARY specifies that the data in the table is temporary where as the
table definition is permanent. In other words, the data is visible only in the session in
which it was inserted, but the table definition is visible in all sessions.

schema is same as the user name

table_name is the name of the table

DEFAULT expr specifies a default value that a column should have

column is name of the column

datatype specifies the datatype and the length of a column

Given below is an example that creates a table named Branch, with columns to
store ID, name, address, location, phone and the year during which the branches
were established.


         CREATE TABLE Branch
         (cBranchID   NUMBER(7),
          cBranchName        CHAR(25),
          vBranchAdress      VARCHAR2(50),
          cBranchLocation CHAR(15),
          cPhone             CHAR(10),
          dEstbl             DATE
         );

When the table is created, the following message is displayed.

         Table created.



© SQL Star International Ltd.                                                        252
To view the columns and their datatypes in the Branch table, issue the command
DESCRIBE in the following manner:

       DESCRIBE Branch




Schema

When a database is created, several users access it. A single user does not create all
the database objects. Database objects are created by each user as and when
required. Database tables are usually created just once as they make up the basic
database.

When many users create objects, there is a security issue. To prevent the users from
tampering with each other‘s objects, every user is allotted a separate work area. A
user is allowed to create database objects in his work area and use them. There is no
physical demarcation of memory area for different users. It is a logical allotment of
memory area. Database objects created by one user are logically separate from the
database objects created by other users. Such logical collection of database objects
such as tables, views or sequences is known as a schema.

For example, the tables named Member and Book are created by the DBA. Hence,
the DBA becomes the owner of the tables and the tables become a part of the DBA
schema.

To reference the objects created by a user, prefix the object name with the schema
or owner name.

For instance, to refer to the Member table you would refer to it as
       DBA.Member

Table Naming Conventions

To improve readability and avoid common mistakes, some naming conventions need
to be followed.

They include:

Keeping short and descriptive names. For example, it would be hard to
comprehend a table named as Bk_iss_trans. Instead, you could name it
Transaction.

© SQL Star International Ltd.                                                     253

Giving same name to the columns having same values in different tables.
For example, category ID are present in Book as well as the Category table. So
give them the same name, cCategoryID.

Rules to be followed when naming tables are:

   All tables must begin with an alphabet.
   All column names must be in lowercase.
   Names can be up to 30 characters long.
   You cannot use non-alphanumeric characters except the underscore (_), the
     dollar sign ($) and the hash mark (#).
   The names must not be the same as that of any other object owned by the
     user.
   The names must not be an Oracle server keyword such as SELECT, CREATE,
     INSERT etc.




Setting Default Values



Specifying default values for columns at the time of creating tables saves the task of
entering values for them during an insert. If a row is inserted without a value for a
column then this option prevents null values from being entered into that column.

Literal values, expressions or SQL functions can be used as the default value.

For example, in the Member table, a default value for the dMembershipDt column
can be defined, so that when new member details are to be inserted, their
membership date is set by default to SYSDATE.

              dMembershipDt DATE DEFAULT SYSDATE


Create Tables Using Subqueries
When a table is created, initially it does not contain any value. A table is populated
using the INSERT statement. However, you can create tables with pre-populated
data. That is, you can create a table with the same structure and data as another
table. You can create a table with pre-populated data by using a subquery in the
CREATE TABLE statement.



© SQL Star International Ltd.                                                       254
The syntax to perform this task is:


         CREATE TABLE <table_name>
         [(column, column…)]
         AS subquery;

Where,

table_name is the name of the table.

column is the name of the column. You need not specify the columns that the table
must have if the subquery SELECT statement retrieves all the columns.

There are certain guidelines that need to be followed.

   While defining columns, mention only the column names and if necessary the
   default
   values. Do not define their datatypes and width.
 The number of columns defined must be the same as the number of columns
   mentioned in the SELECT clause.
 If columns were not defined then the column names of the table created would
   be
   the same as the column names specified in the subquery.

For example, the user DBA creates the IncompleteTransaction table for the library
to store details of those books, which have been issued six months back and have
not yet been returned by members. The data for this table comes from the
Transaction table. Inserting rows into the former table will prove to be quite
cumbersome, if there are large number of members who have not returned books in
the past six months. Instead, these details could be directly populated from the
Transaction table, as both the tables are similar in structure. The code to solve this
problem is:
         CREATE TABLE IncompleteTransaction
         AS
                SELECT * FROM Transaction
                WHERE dIssueDt>(SYSDATE – 6)
                AND dActualReturnDt IS NULL;
         Table created.



The code selects all those details from the Transaction table, where members have
not returned books issued more than six months back and populates them into
IncompleteTransaction table.

         SELECT *
         FROM IncompleteTransaction;

© SQL Star International Ltd.                                                     255
Displays the following output:

CTRANID     CMEMBERID CBOOKID             DISSUEDT DRETURNDT DACTUALRE
NFINE
-------- --------- ------------ --------- --------- --------- -----
T0000300100 CBW109702 ROM020003211 07-SEP-00 21-SEP-00
T0000241000 CRB038901 PSH010000010 11-OCT-00 25-OCT-00



Datatypes Used When Defining Columns

To create tables, you need to decide what kind of data you want to store in the
tables. Are they number or text? This brings us to the issue of datatypes.

Datatypes help us identify the type of data that can be entered in a column. The
datatypes that have been used so far are alphanumeric datatypes such as
VARCHAR2 and CHAR, numeric datatype such as NUMBER and the DATE datatype.

Character Datatype

This datatype is used to store character values.

   CHAR datatype supports character data up to a maximum length of 2000. It
      pads the column value with blanks up to the length declared after taking up
      the required space for the value.
   VARCHAR2 datatype allows you to store character data up to a maximum
      length of 4000. VARCHAR2 does not pad up the blank cells.

In addition to the above datatypes, the other character datatypes available in the
Oracle database are:




Number Datatype
The datatype used to store only numeric data is the number datatype, NUMBER
(precision, scale). It can store both fixed and floating-point numbers. By
precision we mean the total number of digits and scale is the number of digits to the
right of the decimal point. For example, 779.69 is number datatype where the
precision is 5 and the scale is 2.

In the Member table, member‘s age is stored as NUMBER datatype.

© SQL Star International Ltd.                                                        256
Date Datatype

In Oracle, dates are stored in the DATE datatype, which actually contains two values:
the date, and the time between January 1, 4712 BC and December 31, 9999 AD. The
default date format in which Oracle stores date is DD-MON-YY where DD is the day
of the month (01), MON is the month (Jan) and RR is the year (two-digit year-99,
01).



DATETIME Datatype

This datetime datatype had been introduced in Oracle9i. The datetime datatype
includes the time zone in the date and time data, as well as provide support for
fractional seconds. New datetime functions are also provided to use these datatypes.
These datatypes and functions ease the development of applications accessed
globally and significantly reduce the cost of developing and deploying applications.
Applications that are deployed across the globe include time zones and multi-
language support through Unicode. The datetime datatypes are time zone sensitive
and adjust the datetime as per the session time zone of the user.

The datetime datatypes are based on the concept of time zones and Greenwich Mean
Time (GMT), now known as Coordinated Universal Time (UTC). The time along the
prime meridian in Greenwich, England is known as Greenwich Mean Time (GMT). The
meridian line is an imaginary line that runs from the North pole to the South pole.

The earth is divided into 24 time zones depending on the hours of a day. UTC is the
standard time, which is same all around the year. It does not change by summer
time or daylight savings time. All time zones in the world refer to the UTC. When it is
noon in Greenwich, it is midnight along the international line.




The datetime datatypes include:

   TIMESTAMP data type
       TIMESTAMP WITH TIME ZONE
       TIMESTAMP WITH LOCAL TIME
   INTERVAL data type
       INTERVAL YEAR TO MONTH
       INTERVAL DAY TO SECOND

© SQL Star International Ltd.                                                      257
TIMESTAMP Datatype



The TIMESTAMP data type allows time to be stored as a date with fractional seconds.
It is an extension of the DATE datatype and stores the year, month and day of the
DATE datatype along with the hour, minute and seconds. Apart from this, it also
stores the fractional value of seconds. The TIMESTAMP datatype has the following
form:

         TIMESTAMP[(fractional_seconds_precision)]

Where,

fractional_seconds_precision specifies the number of digits in the fractional part of
the SECOND datetime field. It can be any number ranging from 0-9.

For instance, create a table AdmissionDetails with a column of type TIMESTAMP.


         CREATE TABLE AdmissionDetails
         ( StudentName      VARCHAR2(20),
          Address     VARCHAR2(20),
          AdmissionDate TIMESTAMP(7),
          Fees       NUMBER(7,2)
         );

In AdmissionDetails table, the AdmissionDate column is of type TIMESTAMP and
of precision ‗7‘, which indicates the fractional seconds precision. If you do not specify
the precision, the default is 6.

Now, insert two rows into the table. When you execute the following query.

         SELECT admissiondate FROM Admissiondetails;

The output is as follows:

         25-NOV-20 01.00.00.0000000 AM
         01-OCT-20 01.00.00.0000000 AM


The TIMESTAMP datatype has the following variations:
   
   TIMESTAMP WITH TIME ZONE data type
   TIME STAMP WITH LOCAL TIME data type




© SQL Star International Ltd.                                                        258
TIMESTAMP WITH TIME ZONE
TIMESTAMP WITH TIME ZONE datatype is an extension of TIMESTAMP and stores
year, month, day, hour, minute, second with fractional seconds, TimeZone hour and
TimeZone_minute or TimeZone_region. It has the following format:

        TIMESTAMP[(fractional_seconds_precision)] WITH TIME ZONE

Two values of TIMESTAMP WITH TIME ZONE datatype are considered identical if they
represent the same instant in UTC, regardless of the TIME ZONE offset. For instance,

        TIMESTAMP ‗2000-02-15 9:00:00 +8‘

is identical to

        TIMESTAMP ‗2000-02-15 3:00:00 +2‘

Here,

‗+8‘ is the time zone offset of Singapore.
‗+2‘ is the time zone offset of Egypt.

As the difference in the values of the two offsets is six hours, 9:00 AM in Singapore
is same as 3:00 AM in Egypt.

Create a table AdmissionDetails1 with a column admission date of type TIMESTAMP
WITH TIME ZONE. Insert two records and see the output.


        CREATE TABLE AdmissionsDetails1
        (StudentName     VARCHAR2(20),
        Address                 VARCHAR2(20),
        AdmissionDate TIMESTAMP WITH TIME ZONE,
        Fees                    NUMBER(7,2)
        );

        Table created.




Insert some values into the table AdmissionDetails1 by selecting data from
AdmissionDetails table.


        INSERT INTO AdmissionDetails1


© SQL Star International Ltd.                                                      259
SELECT * from AdmissionDetails;

Now, you select the admission date from the newly created table
AdmissionDetails1 table:

       SELECT AdmissionDate from AdmissionDetails1;

Following is the output, which shows the Time Zone offset from UTC, as ‗+5:30‘:


       ADMISSIONDATE
       -------------
       25-NOV-20 01.00.00.000000 AM +05:30
       01-OCT-20 01.00.00.000000 AM +05:30



TIMESTAMP WITH LOCAL TIME ZONE

TIMESTAMP WITH LOCAL TIME ZONE is another variation of the TIMESTAMP
datatype that includes a time zone displacement in its value. Data stored in the
database is converted to the database time zone. However, the time zone offset is
not stored as a part of the column data. When a user selects a data, the server
returns the value according to the user‘s session time zone.

For example, a Singapore database has system time zone offset of ‗+8‘. If a user
from India (with session time zone offset ‗+5.30‘) uses the Singapore database,
TIMESTAMP WITH LOCAL TIME ZONE data is adjusted as follows:

 The user in India inserts a TIMESTAMP value ‗10-NOV-2001 9:00:00 +5:30‘
into a TIMESTAMP WITH LOCAL TIME ZONE column in Singapore database. The
inserted data is stored in Singapore database as ‗10-NOV-2001 11:30:00‘. Note the
difference in time from ‗9:00‘ to ‗11:30‘. This is due to a difference of ‗+2:30‘ hours
between the offset of Singapore and India time zone.

 Later, when the client in India retrieves the same data from Singapore
database, the value displayed in India is‗10-NOV-2001 9:00:00 ‘. The Oracle
database returns the data in the user‘s local session time zone.

 Whereas, a client in Singapore retrieves the same data, the value displayed is
‗10-NOV-2001 11:30:00‘




© SQL Star International Ltd.                                                       260
The format of TIMESTAMP WITH LOCAL TIME ZONE datatype is:

       TIMESTAMP[(fractional_seconds_precision)] WITH LOCAL TIME ZONE

Create a table with TIMESTAMP WITH LOCAL TIME ZONE datatype. Insert some data
into it. Try to retrieve the same data from a different session. You will see the
difference in time, as the Oracle database returns the data in the user‘s local session
time zone.

This session is started in the time zone of India. Later you can change the time zone
and see the difference in time.


       CREATE TABLE AdmissionsDetails2
       ( StudentName     VARCHAR2(20),
        Address      VARCHAR2(20),
        AdmissionDate TIMESTAMP WITH LOCAL TIME ZONE,
        Fees        NUMBER(7,2)
       );

The code creates a table called AdmissionDetails2 with AdmissionDate of type
TIMESTAMP WITH LOCAL TIME ZONE and other columns of their respective
datatypes.

Insert some rows into the table as follows:


       INSERT INTO AdmissionDetails2
       SELECT * FROM AdmissionDetails1;

When you retrieve data within the column AdmissionDate from the table
AdmissionDetails2, the output shows the time as per current time zone:


       SELECT AdmisionDate FROM AdmissionDetails2;




© SQL Star International Ltd.                                                      261
ADMISSIONDATE
       -------------------
       25-NOV-20 01.00.00.000000 AM
       01-OCT-20 01.00.00.000000 AM
       04-MAR-01 09.30.00.000000 PM

Change the time zone to Singapore time zone in the following manner:


       ALTER SESSION SET TIME_ZONE = ‗+8:00‘;
       Session altered.

Now if you select the AdmissionDate column from AdmissionDetails2 table, you
get the following output:


       SELECT AdmisionDate FROM AdmissionDetails2;


       ADMISSIONDATE
       -------------------------
       25-NOV-20 03.30.00.000000 AM
       01-OCT-20 03.30.00.000000 AM
       05-MAR-01 12.00.00.000000 AM

As the difference between time zone of Singapore and time zone of India is two and
a half hours, the time displayed in the output shows a difference of two and a half
hours in each entry. Therefore, a user in Singapore will see the output according to
Singapore local time zone and a user in India will see the output according to Indian
local time zone. This is possible with the help of TIMESTAMP WITH LOCAL TIME
ZONE datatype.

The INTERVAL Datatype

The INTERVAL datatype is used to store a period of time. A period of time is the
difference between two datetime values. The period can be years, months, days,
hours, minutes or seconds. Therefore the interval datatype comprises of two types:

   INTERVAL YEAR TO MONTH datatype
   INTERVAL DAY TO SECOND datatype

The INTERVAL qualifier may specify a leading field precision, which specifies the
number of digits that can be present in a leading field.




© SQL Star International Ltd.                                                       262
INTERVAL YEAR TO MONTH datatype

The INTERVAL YEAR TO MONTH datatype stores a period of time using YEAR and
MONTH datetime fields. It is specified as follows:

       INTERVAL YEAR[(year_precision)] TO MONTH

Where, year_precision is the number of digits in the YEAR datetime field. The default
value of year_precision is ‗2‘.

For instance,
    INTERVAL ‗21-5‘ YEAR(2) TO MONTH indicates an interval of 21 years and 5
      months
    INTERVAL ‗21-5‘ YEAR(2) indicates an interval of 21 years
    INTERVAL ‗5‘ MONTH(2) indicates an interval of 5 months

Create a table LEASE that has a lease_time column of INTERVAL YEAR TO MONTH
datatype, with year_precision value as ‗2‘ and insert some values for year and
month.

       CREATE TABLE Lease
       (
         lease_time INTERVAL YEAR(2) TO MONTH
       );

       Table created.


       INSERT INTO Lease VALUES(INTERVAL ‗10‘YEAR(2));
       INSERT INTO Lease VALUES(INTERVAL ‗11‘ MONTH);
       INSERT INTO Lease VALUES(INTERVAL ‗3-9‘ YEAR TO MONTH);
       INSERT INTO Lease VALUES(‗5-10‘);

       SELECT Lease_time FROM Lease;

The output is:


       LEASE_TIME
       ----------
       +10-00
       +00-11
       +05-10




The first INSERT statement inserts the value for year as ‗10‘. The year takes a
precision of ‗2‘ as specified during table creation. If you try to insert a value of three

© SQL Star International Ltd.                                                          263
digits, Oracle server gives an error. The second INSERT statement inserts a value for
month as ‗11‘. The third INSERT statement inserts values for both year as well as
month as ‗3-9‘.



INTERVAL DAY TO SECOND Datatype

The INTERVAL DAY TO SECOND datatype stores a period of time in days, hours,
minutes and seconds. The format is:

       INTERVAL DAY[(day_precision)] TO SECOND

For instance,

   INTERVAL ‗5 03:15:20‘ DAY TO SECOND indicates an interval of 5 days, 3
       hours, 15 minutes and 20 seconds.
   INTERVAL ‗10 00:00:00‘ DAY TO SECOND indicates an interval of 10 days, 0
       hours, 0 minutes and 20 seconds.

Let us create a table MATCH with a column StartDt of INTERVAL DAY TO SECOND
datatype with a precision value of ‗2‘ and insert some values into it.


       CREATE TABLE Lease1
       (StartDt INTERVAL DAY(2) TO SECOND);


       INSERT INTO Lease VALUES(
            INTERVAL ‗9 02:30:15‘ DAY TO SECOND);
       INSERT INTO Lease VALUES(
            INTERVAL ‗15 10:20:30‘ DAY TO SECOND);


       SELECT * FROM Lease1;


The output is as follows:
       +09 02:30:15.000000
       +15 10:20:30.000000

In the above CREATE statement, when we declare a column of DAY TO SECOND
datatype with a precision value of ‗2‘, it indicates that we can insert a value of two
digits per DAY. If we insert more than two digits, the Oracle server gives an error. In
the first INSERT statement, we inserted a time period of 9 days, 2 hours, 30 minutes
and 15




© SQL Star International Ltd.                                                      264
seconds. In the second INSERT statement, we inserted a time period of 15 days, 10
hours, 20 minutes and 30 seconds.




Datetime Functions

You have seen the various datetime datatypes. Now you will learn about the
datetime functions, which enable you to retrieve the current session and database
time for all datetime datatypes. The datetime functions are:

   CURRENT_DATE
   CURRENT_TIMESTAMP
   LOCALTIMESTAMP
   SYSTIMESTAMP
   DBTIMEZONE
   SESSIONTIMEZONE
   EXTRACT
   FROM_TZ
   TO_TIMESTAMP
   TO_TIMESTAMP_TZ
   TO_YMININTERVAL
   TO_DSINTERVAL
   TZ_OFFSET



CURRENT_DATE

CURRENT_DATE returns current date and time in the session time zone as DATE
datatype (without fractional seconds). The value returned is in the form of Gregorian
calendar date value. In earlier releases, current date and time could be retrieved
using SYSDATE. However, using CURRENT_DATE, you can see the time zone changes
as well. You can change the time zone of a session using the ALTER SESSION
command.

Retrieve the current date and time of the session by giving the following code:

     ALTER SESSION SET NLS_DATE_FORMAT = ‗DD-MON-YYYY HH24:MI:SS‘;


     ALTER SESSION SET TIME_ZONE = ‗+05:30‘;
     SELECT SESSIONTIMEZONE, CURRENT_DATE FROM DUAL;

The output is:

       SESSIONTIMEZONE CURRENT_DATE
       --------------- ------------
       +05:30            19-FEB-2002 15:10:19

Now you alter the session to time zone of Singapore.

© SQL Star International Ltd.                                                     265
ALTER SESSION SET TIME_ZONE = ‗+8:00‘;
       SELECT SESSIONTIMEZONE, CURRENT_DATE FROM DUAL;

The output is:

       SESSIONTIMEZONE         CURRENT_DATE
       --------------- -------------------
       +08:00           19-FEB-2002 17:44:45

As you can see from the output, CURRENT_DATE is relative to the session time zone.
Any change in the session time zone is reflected in the time value.

In the first ALTER SESSION statement, the session is altered to the time zone of
India, whereas, in the second statement the session is altered to the time zone of
Singapore. Therefore, when you retrieve the current date, it shows the time of
respective timezones.



CURRENT_TIMESTAMP



The CURRENT_TIMESTAMP function returns the current date and time of the session
in the form of TIMESTAMP WITH TIME ZONE datatype.

The following code retrieves the SESSIONTIMEZONE and CURRENTTIMEZONE from
‗DUAL‘:


       ALTER SESSION SET TIME_ZONE = ‗02:00‘;
SELECT SESSIONTIMEZONE, CURRENT_TIMESTAMP FROM DUAL;

The output is:


       SESSIONTIMEZONE CURRENT_TIMESTAMP
       --------------- ------------------
       +02:00 19-FEB-02 12.21.06.000001 PM +02:00

As shown in the output, CURRENT_TIMESTAMP returns date and time as
TIMESTAMP WITH TIME ZONE type, with time zone as ‗+2‘.

Now change the time zone to ‗-5‘ as shown below:


       ALTER SESSION SET TIME_ZONE = ‗-05:00‘;
       SELECT SESSIONTIMEZONE, CURRENT_TIMESTAMP FROM DUAL;



© SQL Star International Ltd.                                                        266
The output is:




       SESSIONTIMEZONE           CURRENT_TIMESTAMP
       ---------------   -----------------
       -05:00            19-FEB-02 05.37.07.000001 AM -05:00

The CURRENT_TIMESTAMP returns current date and time with time zone as ‗-5‘.



LOCALTIMESTAMP



The LOCALTIMESTAMP function returns the current date and time in the session time
zone. However, the value returned is of TIMESTAMP datatype. The difference
between CURRENT_TIMESTAMP and LOCALTIMESTAMP functions is that the former
returns a value of type TIMESTAMP WITH TIME ZONE, whereas, the latter returns a
value of type TIMESTAMP. The following code illustrates this difference:

       SELECT CURRENT_TIMESTAMP, LOCALTIMESTAMP FROM DUAL;

The output is:

       CURRENT_TIMESTAMP                            LOCALTIMESTAMP
       --------------                  ------------
       19-FEB-02 05.55.41.000000 AM -05:00 19-FEB-02 05.55.41.000000 AM

Now alter the session:


       ALTER SESSION SET TIME_ZONE = ‗+02:00‘;
       SELECT CURRENT_TIMESTAMP, LOCALTIMESTAMP FROM DUAL;
Displays:

       CURRENT_TIMESTAMP                                  LOCALTIMESTAMP
       -----------------                          -------------
       19-FEB-02 01.01.59.000000 PM +02:00                19-FEB-02
01.01.59.000000 PM

Note the difference between the values returned. The CURRENT_TIMESTAMP returns
the date and time along with the time zone, whereas the LOCALTIMESTAMP does
not.



SYSTIMESTAMP

The SYSTIMESTAMP function returns date and time of the server in TIMESTAMP
format, whereas the SYSDATE function (of previous releases) returns only server
system date and time.
© SQL Star International Ltd.                                                     267
SELECT SYSTIMESTAMP, SYSDATE FROM DUAL;




The output is:


       SYSTIMESTAMP                                           SYSDATE
       ------------------------          ------------------
       19-FEB-02 04.40.05.000000 PM +05:30                19-FEB-2002 16:40:05

Observe that SYSTIMESTAMP returns date and time in TIMESTAMP format.



DBTIMEZONE

The DBTIMEZONE function returns the default database time zone. You can set the
default database time zone at the time of database creation by specifying the
SET TIME_ZONE clause of the CREATE DATABASE statement. If not specified, the
time zone of the operating system where the database is installed is taken as the
default database time zone.

       SELECT DBTIMEZONE FROM DUAL;

The output is:


       DBTIME
       -------
       -05:00

The return value can have the following formats, depending on how the user has
specified the database timezone:
        A character type time zone offset in the format ‗[+ | - TZH:TZM]‘
        A time zone region name
        The output of the above select statement shows that the database time
           zone is ‗-5:00‘:



SESSIONTIMEZONE



The SESSIONTIMEZONE function returns the time zone of the current session. It can
have the following format, depending on the time zone specified during database
creation:
       A character type time zone offset in the format ‗[+ | - TZH:TZM]‘
       A time zone region name
© SQL Star International Ltd.                                                     268
Give the following statement to view the session‘s time zone:

       SELECT SESSIONTIMEZONE FROM DUAL;




The output is:


       SESSIONTIMEZONE
       ---------------
       +05:30

Observe that the values for database time zone and session time zone are different .



EXTRACT

The EXTRACT expression extracts the value of a specified datetime field from a
datetime or interval field value. Using the EXTRACT function, you can extract any of
the components specified in the EXTRACT function syntax:


SELECT EXTRACT([YEAR][MONTH][DAY][HOUR]
      [MINUTE][SECOND][TIMEZONE_HOUR]
      [TIMEZONE_MINUTE][TIMEZONE_REGION]
      [TIMEZONE_ABBR]
      FROM [datetime_value_expression]
          [interval_value_expression]);

When you extract -
  
  A TIMEZONE_REGION or TIMEZONE_ABBR (abbreviation), the return value is a
      string containing the appropriate time zone name or abbreviation
  From a datetime with a time zone, the value returned is in UTC
  Any other values, the value returned is in Gregorian calendar format.




The following query extracts the month from the system date:

       SELECT EXTRACT (MONTH FROM SYSDATE) FROM DUAL;

© SQL Star International Ltd.                                                    269
The output is:

       EXTRACT(MONTHFROMSYSDATE)
       -------------------------
                   5

Give the following query to extract the year from the membership date of all the
members belonging to grade ‗B‘:

SELECT EXTRACT (YEAR FROM dMembershipDt) from Member WHERE cGrade =
‘B’;

The output is:

       EXTRACT(YEARFROMDMEMBERSHIPDT)
       ------------------------------
                               1990
                               1997
                               1999
                               2001
                               1994
                               1997

       6 rows selected.



FROM_TZ



The FROM_TZ function converts a timestamp value to a TIMESTAMP WITH TIME
ZONE value. The syntax of the FROM_TZ function is:

       FROM_TZ(timestamp_value, time_zone_value)

Where time_zone_value is a character string in the format ‗TZH:TZM‘ or a character
expression that returns a time zone region string TZR, like ‗ Asia/Singapore‘ or
‗America/Chicago‘.

For instance, to convert to the time stamp value of the date 25th May‘2001 to a TIME
STAMP WITH TIME ZONE value, give the following query:

       SELECT FROM_TZ(TIMESTAMP ‗2001-05-25 10:15:20‘, ‗5:00‘)
       FROM DUAL;

The output is:

       FROM_TZ(TIMESTAMP‘2001-05-5 10:15:20',‘5:00')
       ---------------------------------------------
       25-MAY-01 10.15.20.000000000 AM +05:00

© SQL Star International Ltd.                                                      270
Alternatively, you can also specify the TZR (time zone region) name in the query as
follows:

         SELECT FROM_TZ(TIMESTAMP ‗2001-05-25 10:15:20‘, ‗Asia/Singapore‘)
         FROM DUAL;




The output is:

         FROM_TZ(TIMESTAMP‘2001-05-2510:15:20',‘ASIA/SINGAPORE‘)
         -------------------------------------------------------
         25-MAY-01 10.15.20.000000000 AM ASIA/SINGAPORE




TO_TIMESTAMP

The TO_TIMESTAMP function is used to convert a string of CHAR, VARCHAR2,
NCHAR, or NVARCHAR2 datatype to a TIMESTAMP datatype. The syntax is:

         TO_TIMESTAMP (char,[fmt],[‗nlsparam‘])

Where,

fmt is optional. It specifies the format of char. However, if it is not specified, the
string must be in the default format of TIMESTAMP datatype.
nlsparam is also optional. It specifies the language in which day and month names
and abbreviations are returned. It can have the form:

         ‗NLS_DATE_LANGUAGE = language‘

If not specified, the TO_TIMESTAMP function takes the default language selected for
your session.

To convert a date specified as string to a TIMESTAMP value, give the following query:

         SELECT TO_TIMESTAMP(‗2001-11-25 10:15:20‘,‘YYYY-MM-DD HH:MI:SS‘)
         FROM DUAL;




© SQL Star International Ltd.                                                        271
The output of the above query is:

         TO_TIMESTAMP(‗2001-11-2510:15:20‘,‘YYYY-MM-DDHH:MI:SS‘)
         -------------------------------------------------------
         25-NOV-01 10.15.20.000000000 AM




Observe that the TO_TIMESTAMP function converts the date specified in YYYY-MM-
DD format to TIMESTAMP datatype format which is DD-MON-YY.



TO_TIMESTAMP_TZ

The TO_TIMESTAMP function is used to convert a string of CHAR, VARCHAR2, NCHAR
or NVARCHAR2 datatype to a TIMESTAMP WITH TIME ZONE datatype. The syntax is:

         TO_TIMESTAMP_TZ (char,[fmt],[‗nlsparam‘])

Where,

- fmt is optional. It specifies the format of char. However, if it is not specified, the
string must be in the default format of TIMESTAMP WITH TIME ZONE datatype.
- nlsparam is also optional. It specifies the language in which day and month names
and abbreviations are returned. It can have the form:

         ‗NLS_DATE_LANGUAGE = language‘

If not specified, the TO_TIMESTAMP function takes the default language selected for
your session.

To convert a date specified as string to a TIMESTAMP WITH TIME ZONE value, give
the following query:

         SELECT TO_TIMESTAMP_TZ(‗2002-01-12 10:15:20 +8:00‘,‘YYYY-MM-DD
         HH:MI:SS TZH:TZM‘) FROM DUAL;




© SQL Star International Ltd.                                                        272
The output of the above query is:

  TO_TIMESTAMP_TZ(‗2002-01-1210:15:20+8:00‘,‘YYYY-MM-DHH:MI:SSTZH:TZM‘)
  ---------------------------------------------------------------------
  12-JAN-02 10.15.20.000000000 AM +08:00

Observe that the output displays the time zone also. The TO_TIMESTAMP_TZ
function converts the date specified in YYYY-MM-DD format to TIMESTAMP WITH
TIMEZONE datatype format, which is DD-MON-YY.




TO_YMINTERVAL

The TO_YMINTERVAL function is used to convert a string of CHAR, VARCHAR2,
NCHAR or NVARCHAR2 datatype to an INTERVAL YEAR TO MONTH datatype. The
INTERVAL YEAR
TO MONTH datatype stores a period of time using the YEAR and MONTH datetime
fields. The format of the INTERVAL YEAR TO MONTH is as follows:

         INTERVAL YEAR [(year_precision)] TO MONTH

Where,

year_precision is the number of digits in the YEAR datetime field. The default is 2.

The syntax of TO_YMINTERVAL function is:

         TO_YMINTERVAL(char)

Here, char is the string to be converted.

To calculate a lease period that is one year and two months after current date, give
the following query:

         SELECT SYSDATE,SYSDATE+TO_YMINTERVAL(‘01-02') AS LEASE_PERIOD
         FROM DUAL;

The output is:

         SYSDATE       LEASE_PERIOD
         ------- -------------
         20-FEB-02 20-APR-03

In the above query, the current date is first retrieved. Then a period of one year and
two months is added to it and displayed as lease period.



© SQL Star International Ltd.                                                      273
TO_DSINTERVAL

TO_DSINTERVAL converts a character string of CHAR, VARCHAR2, NCHAR or
NVARCHAR2 datatype to an INTERVAL DAY TO SECOND type. The INTERVAL DAY TO
SECOND datatype stores a period of time using the DAY and SECOND datetime
fields. The format of the INTERVAL DAY TO SECOND is as follows:

         INTERVAL DAY [(day_precision)] TO SECOND

Where,

day_precision is the number of digits in the DAY datetime field. The default is 2.

The syntax of TO_DSINTERVAL function is:

         TO_DSINTERVAL(char)

Here, char is the string to be converted.

To calculate a lease period that is fifty days, ten hours after current date, give the
following query:

         SELECT SYSDATE,SYSDATE+TO_DSINTERVAL(‘50 10:00:00') AS
         LEASE_PERIOD
         FROM DUAL;

The output is:

         SYSDATE LEASE_PERIOD
         ------- ------------
         29-MAY-07 18-JUL-07

In the above query, the current date is first retrieved. Then a period of fifty days, ten
hours is added to it and displayed as lease period.



TZ_OFFSET

Every time zone across the globe has a corresponding offset. The TZ_OFFSET
function returns the corresponding time zone of the value entered depending on the
date when the statement is executed. For instance, if the return value of the
TZ_OFFSET function is –5:00, it indicates that the time zone from where the
statement was executed is
five hours after UTC. If it is +2:00, the time zone is two hours ahead of UTC.

The TZ_OFFSET function can take :

   A valid time zone name
   A time zone offset from UTC, (which returns itself)
   The keyword SESSIONTIMEZONE
   The keyword DBTIMEZONE

© SQL Star International Ltd.                                                        274
The syntax of the TZ_OFFSET function is:

       TZ_OFFSET ([‗time_zone_name‘] [‗[+ | -] hh:mm‘]
       [SESSIONTIMEZONE] [DBTIMEZONE]

To find out the time zone offsets of the regions America/Chicago and Asia/Singapore,
give the following statements:

       SELECT TZ_OFFSET(‗America/Chicago‘) FROM DUAL;

The output is:

       America/Chicago Time Zone is:

       TZ_OFFSET
       ---------
       -06:00

       Asia/Singapore Time Zone is:

       SELECT TZ_OFFSET(‗Asia/Singapore‘) FROM DUAL;

       The output is:

       TZ_OFFS
       -------
       +08:00

The return values indicate that America/Chicago time zone is six hours behind UTC
and Asia/Singapore time zone is eight hours ahead of UTC.

To find out the time zone offset of the current session, give the following statements:

       SELECT TZ_OFFSET(SESSIONTIMEZONE) FROM DUAL;

The output is:

       TZ_OFFSET
       ---------
       +05:30

The session time zone is five and a half hours ahead of the UTC.

To find out the time zone offset of the region where the database is installed, give
the following statement:

       SELECT TZ_OFFSET(DBTIMEZONE) FROM DUAL;

The output is:


© SQL Star International Ltd.                                                      275
TZ_OFFS
       -------
       -05:00

The database time zone is five hours behind the UTC.




Modifying Table Structure
Once a table has been created in the database, it does not necessarily mean that the
table structure is permanent. It can also be modified depending on the need to do
so.

For example, the developer would have defined the length of the book name column
as 20 at the time of creating the Book table. But, while attempting to insert the
details of the book ‗The Strange Case Of Dr. Jekyll And Mr. Hyde‘, the Oracle server
would generate an error as the length of the book name does not match the column
length defined. This problem necessitates changing the column length.
Apart from this, there can be various other instances where you may need to change
the table structure.
This brings into the picture the following changes that a table structure may
undergo.

   Changing column definitions
      Adding new columns
      Changing the definitions of the existing columns
      Removing columns altogether

   Changing table definitions
       Removing tables from the database
       Renaming tables

Manipulating Column Definitions
After creating a table, you would need to change its structure if:

   A column has been omitted while creating the table
   The data being inserted into a column does not conform to the column
      definition
   An unwanted column has been added to the table at the time of its creation

© SQL Star International Ltd.                                                     276
Column definitions can be manipulated using the ALTER TABLE statement.



The ALTER TABLE Statement
The ALTER TABLE statement is used to:

   Add new columns
   Modify existing columns
   Remove columns
   Mark columns as unused

Adding Columns

At the time of creating tables, only those columns that are considered to be
important are created. But at a later stage, new columns may need to be added to
the table.

Using the ALTER TABLE statement with the ADD clause can help. The syntax for
adding a column is,


         ALTER TABLE <table_name>
         ADD (column datatype [DEFAULT expr] [, column datatype]…);

Where,

table_name is the name of the table

column is the name of the column to be added

datatype is the datatype and the width of the new column

DEFAULT expr is the default value that may be specified for the new column

For example, at the time of creating the Member table, the developer may have
omitted the creation of a column to store the email IDs of members. But later, due
to the wide usage of email facilities, he decides to add a column to store email IDs of
members. The database developer can add this additional column by using the
ALTER TABLE statement.


         ALTER TABLE Member
         ADD (cEmailID CHAR (50));

When the table is altered successfully you will see the following message.

         Table altered.

Points to remember


© SQL Star International Ltd.                                                      277
While adding a new column, you cannot specify where it is to appear in the
       table. The new column is always the last column.
   A new column added to a table (already containing rows of data) is initially
       NULL for all the rows.
   If a column with NOT NULL constraint is to be added, then:
           1 The column must first be added to the table without the constraint.
           2 It must be populated with data in all the rows.
           3. Once the column values are not null, the NOT NULL constraint can be
               added to it.
   In a table, only one column can be of LONG and LONG RAW datatype.
       Therefore, you cannot add columns of LONG and LONG RAW datatypes if the
       table already has columns of these datatypes.



Modifying Columns

While creating tables, columns are defined along with their datatypes and lengths in
order to identify the type of data that the columns can hold. In case you want to
alter the column to hold values larger than the current ones then the new column
length must be made larger.

This can be done by using the ALTER TABLE statement with the MODIFY clause. The
syntax for modifying a column is:


       ALTER TABLE <table_name>
       MODIFY [column datatype [DEFAULT expr] [, column datatype]…);

For example, in the Book table, the column cBookName is defined of length 20.
But, while attempting to enter details of book ‗The strange case of Dr. Jekyll and Mr.
Hyde‘, the Oracle server would generate an error because the book name happens to
be longer than the length defined for the column. Therefore, modify the column
width so as to accommodate long book names.


       ALTER TABLE Book
       MODIFY (cBookName CHAR (100));

In the code, the length of the cBookName column has been changed from 20 to
100.

In addition to changing the column length, the column datatype and default value
can also be changed.




Points to remember:
      


© SQL Star International Ltd.                                                     278
Increasing column length using the MODIFY clause is OK, but decreasing them or
changing the column datatype tends to be tricky. For example, if the column length
of cMemberID were reduced from 9 to 7, then all those members having IDs of
lengths more than 7 would not satisfy the column definition and would therefore get
truncated.


         ALTER TABLE Member
         MODIFY cMemberID CHAR (7);

         ERROR at line 2:
         ORA-01441: column to be modified must be empty to decrease column
               length

In order to overcome this problem, some special steps need to be taken.
           
           Before reducing the column length, ensure that the column has all null
              values.
           But before deleting all the values from the column in question, create
              a temporary table to store the values of the column. This can be done
              by using the CREATE TABLE AS SELECT statement, where the SELECT
              statement extracts data from the primary key column and the column
              that is to be modified.
Changing the DEFAULT value of a column affects only succeeding insertions to
the column.

Dropping Columns
Columns are dropped when you no longer need them from a table. The DROP
COLUMN clause with the ALTER TABLE statement is used to remove a column. This
feature is available only from Oracle8i. The syntax for dropping columns is,


         ALTER TABLE <table_name>
         DROP COLUMN <column_name>;

Where,

<column_name> specifies the column that is to be dropped.

For example, the developer creates the Category table with the following columns:

   cCategoryID
    cCategoryCode
    cCategoryName



         CREATE TABLE Category
         (cCategoryID    CHAR (5) PRIMARY KEY,
         cCategoryCode   CHAR (4),

© SQL Star International Ltd.                                                   279
cCategoryName     CHAR (15)
       );

But after creating the table, the developer realizes that both the cCategoryID and
cCategoryCode columns hold the unique identity numbers given to each category.
Therefore, one of them must be removed from the table structure. This can be done
using the DROP clause as follows:


       ALTER TABLE Category
       DROP COLUMN cCategoryCode;




Points to remember

   The dropped column may or may not contain data.
   At a time only one column can be dropped.
   The table must have at least one column left after one of its columns has been
      dropped.
   A dropped column cannot be recovered.




Mark Columns as UNUSED

The database developers or administrators could feel that some columns in a table
are not appropriate or not required to be included in the table. Therefore, they would
decide to drop these columns from their respective tables. But the response time
taken for executing a DROP clause is quite slow. This is because dropping of columns
using the DROP clause results in the restoration of the storage disk space. Also,
dropping of columns could come in the way of any transaction that is currently
accessing the database and system resources.

© SQL Star International Ltd.                                                     280
Therefore, to speed up the response time you could mark the columns to be dropped
as unused. Doing so does not restore the disk space. Instead, the columns so
marked could later be dropped when the requirement for the system resources is
less. The option used to mark one or more columns as unused is the SET UNUSED
option.

The syntax to mark columns as unused is,


         ALTER TABLE <table_name>
         SET UNUSED (<column_name>);

or,


         ALTER TABLE <table_name>
         SET UNUSED COLUMN <column_name>;


Where,

SET UNUSED COLUMN are the keywords to mark the column

table_name is the table name

column_name is the column name

For example, the New Jersey Central Library decides to drop the cMaritalStatus
column from the Member table. But the database developer or administrator
considers the option of dropping the column during the library hours as not
advisable. This is because the act of dropping the column could come in the way of
users accessing the table.

Therefore, they decide to mark it as unused and drop it probably after library hours
when the demand on the resource is less.


         ALTER TABLE Member
         SET UNUSED (cMaritalStatus);
         Table altered.


On marking cMaritalStatus as unused, it is treated as if it were dropped. But on
marking it as unused:

      Its values are not removed from each row in the table. Meaning that the disk
          space used by it is not restored.
      As the disk space is not restored, the response time is faster when executing
          the SET UNUSED option.

© SQL Star International Ltd.                                                       281
 Though the column data remains in the table‘s rows, you cannot access it by
      using the ‗SELECT *‘ query. Also, the column will not be displayed even by
      issuing the DESCRIBE command.


       SELECT cMemberID,cBranchID,cMaritalStatus
       FROM Member;

Displays the following error message:


       SELECT cMemberID,cBranchID,cMaritalStatus
                             *
       ERROR at line 1:
       ORA-00904: invalid column name

It will also not be displayed when you describe the structure of the table.


       DESCRIBE Member
       Name          Null?            Type
       --------         ---------     -------
       CMEMBERID          NOT NULL CHAR(9)
       CFIRSTNAME         NOT NULL CHAR(20)
       CLASTNAME          NOT NULL CHAR(20)
       VADDRESS         NOT NULL VARCHAR2(50)
       CAREA          NOT NULL        CHAR(10)
       CZIPCODE        NOT NULL       CHAR(7)
       CPHONE                       CHAR(10)
       NAGE                      NUMBER(2)
       DMEMBERSHIPDT                  DATE
       CGRADE                    CHAR(1)
       CBRANCHID                     CHAR(7)




A new column with the same name as the unused column can be added to the
table.


       ALTER TABLE Member
       ADD cMaritalStatus CHAR (1);

The disk space occupied by cMaritalStatus column, which is marked unused cannot
be restored. However, if you want to reclaim the disk space, you can drop the
© SQL Star International Ltd.                                                  282
unused column. Use the DROP UNUSED COLUMNS option to do this. The syntax for
the same is:


      ALTER TABLE <table_name>
      DROP UNUSED COLUMNS;

To drop the unused column from Member table:-


      ALTER TABLE Member
      DROP UNUSED COLUMNS;

This statement removes the marked column from the Member table.

However, if you would have dropped the cMaritalStatus column using the DROP
clause, then

                     The disk space used by the column is restored. This means that
                      values of cMaritalStatus are removed from each row in the
                      table and the space occupied by it is now available for any
                      further use.
                     As the disk space has to be restored, the response time taken
                      by executing the DROP COLUMN clause is slower.
                     The data stored in cMaritalStatus is lost and cannot be
                      recovered.
                     Executing a ‗SELECT *‘ query will not retrieve data from
                      cMaritalStatus.




Manipulating Table Definitions
There may arise circumstances when you would have to make major modifications to
the database. These modifications could be related to changing or removing the
definition of a table, such as:

   Giving the table a new name
   Truncating a table i.e. deleting rows without affecting its definition
   Dropping the table altogether

© SQL Star International Ltd.                                                   283
These modifications are done using DDL commands.
Dropping Tables
If the basic need of a database changes, then you would have to make some
changes to the tables created within the database. In order to drop a table, the
DROP TABLE command is used. Its syntax is:

         DROP TABLE <table_name>;

Where,

table_name is the table that is to be dropped.

In case you want to delete the Member table issue the following command.

         DROP TABLE MEMBER;

A point to remember is that dropping tables is not simple. Before issuing the DROP
TABLE command ensure that no other table references the table to be dropped. In
other words, there should be no foreign key columns referencing the table. In case
you go ahead and issue the command you will see the following error message.

ORA-02449: unique/primary keys in table referenced by foreign keys

To overcome this you must use the CASCADE CONSTRAINTS clause with the DROP
TABLE command. Using this clause drops the constraints that refer to the table being
dropped.

In the above example, the Member table has a primary key constraint that is being
referenced by a foreign key constraint of Transaction table. Therefore, to overcome
this error use the CASCADE CONSTRAINTS clause as follows:


         DROP TABLE Member
         CASCADE CONSTRAINTS;

The code executed is irreversible. This is because the DROP command is a DDL
command. You can confirm this by trying to rollback the statement. When you issue
the ROLLBACK command you get the following message:

         Rollback complete.

This message implies that the rollback activity has been completed. Issue the
DESCRIBE command to check if the table still exists. On doing so the following
message is displayed:

    ORA-04043: object Member does not exist

Points to remember while using the DROP TABLE command:

The table definition is removed from the database
Data stored within the table is deleted
© SQL Star International Ltd.                                                      284
 You cannot roll back the DROP TABLE command. Being a DDL command it is
auto
    commit by nature.


Flashback Table

A table can be reinstated automatically using a new 10g feature referred to as
Flashback table feature.
Here is a scenario that happens more often:
A user drops a very important table accidentally, and it needs to be recovered as
soon as possible.
Use the Flashback Table feature, which makes the recovery of a dropped table as
easy as the execution of a few statements.

Let‘s see with an example, how this feature works.


Drop the Member table of the library application

       SQL> DROP TABLE Member;

Displays:

       Table dropped.

Let‘s check the status of the table now.

       SQL> SELECT * FROM tab;

       TNAME                         TABTYPE       CLUSTERID
       -----------------------------   ----------    ----------
       cpndanfgMAAAAAANPw==$0                     TABLE

The table Member is gone but note                 the   presence   of   the   new   table
BIN$04LhcpndanfgMAAAAAANPw==$0.


Here‘s what happened:
The dropped table Member, instead of completely disappearing, was renamed to a
system-defined name. It stays with the same structure as that of the original table.
If there are indexes defined on the table, they are renamed too, using the same
naming convention used by the table.
The table and its associated objects are placed in a logical container known as the
―Recycle Bin,‖ which is similar to the one we have in our PC. The Recycle Bin is
merely a logical structure that catalogs the dropped objects. Use the following steps
to restore the dropped table back.

      SQL> SHOW RECYCLEBIN

ORIGINAL-NAME RECYCLEBIN-NAME                      OBJECT- DROP TIME
                                                          TYPE

© SQL Star International Ltd.                                                        285
------------- ----------------------------- -------   -------------------

RECYCLETEST      BIN$04LhcpndanfgMAAAAAANPw==$0 TABLE                   2007-05-
19:16:31:10

This shows the original name of the table, RECYCLETEST, as well as the new name in
the Recycle Bin, which has the same name as the new table we saw created after
dropping the table. (Note: The internal Name given may be OS dependent) To
reinstate the table, all you have to do is use the FLASHBACK TABLE command:
       SQL> FLASHBACK TABLE Member TO BEFORE DROP;

       FLASHBACK COMPLETE.

       SQL> SELECT * FROM TAB;

       TNAME            TABTYPE                CLUSTERID
       -------------- -----------              -----------
       MEMBER            TABLE

But what if you want to drop the table completely, without needing a flashback
feature. In that case, you can drop it permanently using:
       DROP TABLE MEMBER PURGE;

This command will not rename the table to the Recycle Bin name, rather, it will be
deleted permanently, as it would have been pre-10g.


Managing the Recycle Bin

       PURGE TABLE Member;
Or using its Recycle Bin name:
       PURGE TABLE ―BIN$04LhcpndanfgMAAAAAANPw==$0‖;

This command will remove table MEMBER and all dependent objects such as indexes,
constraints, and so on from the recycle bin, saving some space. If, however, you
want to permanently drop an index from the recycle bin, you can do so using:
       PURGE INDEX in_Member_01;

This will remove the index only, leaving the copy of the table in the recycle bin.

Truncating Tables
The TRUNCATE TABLE statement is a part of the Data Definition Language that
performs high-speed data deletion.

The TRUNCATE statement deletes data from tables just as the DELETE statement,
but with a slight difference. The difference being in the speed with which the deletion
is performed by the two statements.

The DELETE statement uses the transaction processing control commands for the
completion of its task. That is, the task performed by a DELETE statement is not
considered to be complete unless the task is committed to the database. This makes


© SQL Star International Ltd.                                                        286
it a very slow process. Therefore, using the DELETE statement proves to be an
inefficient option when the task is to remove data from a large table.

On the other hand, the TRUNCATE statement bypasses the transaction processing
control commands because the task gets automatically committing on execution of
the statement. If a user were sure that he or she wants to delete a large number of
rows from a table, then using the DELETE option would prove to be time consuming.
Therefore, executing the TRUNCATE statement immediately deletes all rows from a
table releasing the storage space occupied by them. This is the reason why the
TRUNCATE statement is known as the high-speed data deletion statement. The
syntax for truncating a table is:

         TRUNCATE TABLE <table_name>;

Truncate the Member table from the library database

         SQL>TRUNCATE TABLE Member;

This statement removes all row data from the Member table.

Points to remember while using the TRUNCATE statement:

 Data from all rows are deleted, but the table definition including the definition of
    constraints remains intact.
 The storage space occupied by all rows is released.
 As it is a DDL statement, data once deleted cannot be recovered.




Changing Table Names
At times you might have to change the names of tables in case they have not been
named according to the naming conventions of the organization or if a newly created
table is to be given a name as that of an already existing table. You can change the
name of a table with the RENAME statement. Its syntax is:

         RENAME <old_name> TO <new_name>;

Where,

old_name is the old name of the table.

© SQL Star International Ltd.                                                       287
new_name is the new name with which it is to be replaced.

You created a table Publisher to store details of publishers. You want to make the
name more self-explanatory and want to change it to PublisherDetails. In order to
this, issue the following statement:

       SQL> RENAME Publisher TO PublisherDetails;

In the example, the RENAME statement changes the name of the Publisher table to
PublisherDetails. The message displayed is:

       Table renamed.




Data Dictionary Tables
The tables you have worked with, were all created and maintained by developers
such as yourself. But in addition to these tables, Oracle server provides tables that
are not created by developers. They are known as Data Dictionary tables. More
discussion on this will be done separately later.




© SQL Star International Ltd.                                                       288
Summary

In this chapter, you have learnt that:

        Data Definition commands (DDL) are used to create and manage database
       objects in a schema.
        Schema is a collection of database object. The word SCHEMA and USER are
       interchangeable.
        DDL commands are CREATE: creates new database object, ALTER: modify
       the structure of the database object, DROP: removes the database object
       from the schema, RENAME: gives a new name to the database object,
       TRUNCATE: removes rows permanently leaving the structure intact .
      New tables can be created using an existing table using a subquery in the
       CREATE TABLE statements.
      Datatypes such as VARCHAR2, CHAR, NUMBER, DATA and various
       TIMESTAMP determine the type of data a column can hold.
      FLASHBACK statement can be used to restore the dropped objects.
      Dropped objects of a schema can be viewed using SHOW RECYCLE BIN
       command.
      Table can be removed from the recycle bin using PURGE command.




© SQL Star International Ltd.                                               289
Lab Exercise
1.    Create a table Dept_details based on the details given in the following chart.
      Save the syntax in a script named LabEx12_01.sql. Execute the script and
       confirm that the table has been created.




2.    Populate the Dept_details table with data from Departments table. Insert
      only the columns that you need.

3.    Create a table Emp_details based on the following chart.




© SQL Star International Ltd.                                                    290

4.  Modify the empFirstName and empLastName columns in the Emp_details
         table to allow for longer names.
         Table altered.




5.   Create a table emp2 based on the structure of employees table. Include the
      columns employee_id, first_name, last_name, department_id, job_id,
       and salary into the Emp2 table.




6.   Drop the Emp_details table.
7.   Rename the table Emp2 as Emp_details.
8.    Drop the column first_name from the table Emp_details and see the
       structure of the table




© SQL Star International Ltd.                                                 291
.     Make the job_id column of Emp_details table UNUSED and confirm the
       modification.

10   Drop all the unused columns from Emp_details table, confirm
       the modification.





11.Create a table New_Emp having employee details, and hire date as
           TIMESTAMP datatype.




12. Modify the table New_Emp with hiredate as TIMESTAMP WITH TIMEZONE
           datatype. View the structure of the table.




13.    Try the following:
a) Create table test with column specified below:
       x NUMBER
b) Select all the tables from present schema.
c) Drop the Test table from schema.
d) Select all the tables from current schema and see the change.
e) Display the contents of RecyleBin
f) Write the command to reinstate the table.

© SQL Star International Ltd.                                                  292
g) Select all the tables from current schema.
h) Drop the table completely without flashback feature or drop it permanently.
i) What command is used to remove the table from Recycle Bin after the table is
dropped.




© SQL Star International Ltd.                                                     293
Chapter 13




                                   Managing Constraints

                                               Introduction to Constraints
                                   Defining Constraints at different level
                                Explain the different types of Constraints
                                                      Creating Constraints
                                                     Deferring Constraints
                                                     Dropping Constraints
                                  Enabling and Disabling the Constraints
                                Querying Data Dictionary for Constraints




© SQL Star International Ltd.                                         294
Objectives

At the end of this chapter, you will be able to:

     Understand Integrity constraints

     Maintain Integrity constraints

     Understand Deferred Constraints

     Understand Dictionaries related to constraints




© SQL Star International Ltd.                          295
Enforce Business Rule
In any organization, Data plays an important role in its day to day functioning.
In order to prevent entry of invalid data into tables, Oracle server uses a mechanism
called constraints. Constraints (also known as data integrity constraints) are mainly
used to enforce business rules. They ensure accuracy and consistency of data in a
relational database.

Referential Integrity Constraints therefore ensure that:

     Inserting,  updating and deleting of rows from a table succeed only if the
          constraints are satisfied.

        Parent tables (those tables on which other tables are dependent) are not
          deleted.




Defining Constraints

Constraints can be defined before or after the table creation. There are two levels for
defining a constraint:

       Column level

       Table level



Column Level Constraints

Column level constraints are defined within the column specification and reference
only a single column. Hence, they enforce restriction on the type of data that can be
entered into that column. The syntax is:


         CREATE TABLE <table_name>
         <column_name> datatype,. . .
          [CONSTRAINT <constraint_name>] <constraint_type>,….


Where,

column_name is the name of the column for which the constraint is to be defined.

datatype specifies the type of data that can be entered into the column.

CONSTRAINT constraint_name assigns a name to the constraint that is being defined
for the column. This clause is not mandatory.
constraint_type specifies the type of constraint being defined. Different constraint
types are covered next.

© SQL Star International Ltd.                                                      296
Table Level Constraints

Table level constraints are defined separately from the column specifications and can
reference one or more columns. They enforce restrictions on the type of data that
can be entered into the table. All constraints except NOT NULL can be defined at this
level. The syntax is:


         CREATE TABLE <table_name>
         <column_name> datatype,. . .
         [CONSTRAINT <constraint_name>] <constraint_type>
             (column, ….)


Where,

constraint_name is name of the constraint.

constraint_type is the type of constraint.




Types of Constraints


The data integrity constraints used to enforce business rules are:

         NOT    NULL: This constraint prevents null values from being entered into a
                         column.
         UNIQUE: This constraint ensures that the column values or combination of
                       column values is unique for all rows in the table.
            PRIMARY KEY: This constraint prevents null values into the column and
                          identifies each row of a table uniquely.
         
         
         
         FOREIGN      KEY: A foreign key constraint establishes a parent-child
                             relationship by ensuring that the child column

© SQL Star International Ltd.                                                     297
referencing the parent column has same values or are
                               null.
       CHECK: A Check constraint checks whether a particular condition is met or
                   not.



The NOT NULL Constraint

The NOT NULL constraint ensures that null values are prevented from being entered
into columns.

There can be instance, where some columns in a table can not have null values. For
example, when a person registers himself as a member, the librarian must
necessarily fill in his name, address and age in the Member table. This is because
they are all vital pieces of information that cannot be done away with. Therefore, by
defining these columns as
NOT NULL, you ensure that null values are not entered into them.

Create the Member table with constraints to prevent null values from being entered
into member‘s name, address and age.


       CREATE TABLE Member
       (cMemberID         CHAR (9),
        cFirstName CHAR (20) NOT NULL,
        cLastName     CHAR (20) NOT NULL,
        vAddress     VARCHAR2 (50) NOT NULL,
        cArea       CHAR (10) NOT NULL,
        cZipcode     CHAR (7) NOT NULL,
        cPhone      CHAR (10),
        nAge        NUMBER (2) NOT NULL,
        dMembershipDt DATE DEFAULT SYSDATE,
        cGrade      CHAR (1),
        cBranchID CHAR(7)
       );


In the above code, all the NOT NULL constraints are defined at the column level.
Since the constraints are unnamed, the Oracle server will generate names for them.
You can however name the constraints while defining them along with the column
specification as follows:

       CFirstName CHAR (20) CONSTRAINT MemberFNameNN NOT NULL,



The UNIQUE KEY Constraint
© SQL Star International Ltd.                                                    298
A UNIQUE KEY constraint ensures that no two rows of a table have identical values in
a column or a collection of columns. UNIQUE KEY constraints allow the entry of null
values unless NOT NULL constraint is defined for the same column. A UNIQUE KEY
can be defined at the column level or table level.

How would you ensure that two rows of the Branch table do not have the details of
the same branch? You could do so with the following DDL statement.


       CREATE TABLE Branch
       (cBranchID      NUMBER (7),
        cBranchName      CHAR (25) CONSTRAINT BranchNameUK UNIQUE,
        vBranchAdress VARCHAR2 (50),
        cBranchLocation CHAR (15),
        cPhone        CHAR (10),
        dEstbl       DATE
       );


In the code, the cBranchName column has been defined as UNIQUE specifying that
the column cannot have duplicate branch names. This is a column level constraint
definition.

A UNIQUE constraint is defined at the table level, usually if it comprises a collection
of columns.

A UNIQUE KEY constraint defined for a group of columns is known as a composite
unique key. It ensures that the combinations of values in the columns are unique.

To define a composite UNIQUE KEY constraint on the Book table to ensure that the
book name and the publishing year of each book are unique, create the Book table
in the following manner.


       CREATE TABLE Book
       (cBookID     CHAR (13),
       cBookName      CHAR (20) NOT NULL,
       cAuthorName CHAR (30) NOT NULL,
       cCategoryID CHAR (5),
       cPublisherID CHAR (6),
       dPublishedYr DATE,
       cBranchID     CHAR (7),
       nNoOfCopies NUMBER (2),
       CONSTRAINT BkNamePublishYrUK UNIQUE (cBookName, dPublishedYr)
       );
© SQL Star International Ltd.                                                      299
The PRIMARY KEY Constraint

A PRIMARY KEY constraint on a column or a collection of columns helps to uniquely
identify each row in a table. A PRIMARY KEY constraint defined for a collection of
columns is known as a Composite Primary key.

The primary key constraint ensures that any value entered in the columns that is
part of the primary key constraint must be unique for all rows. And they must not
contain null values.

Suppose the library desk officer wants to retrieve the details of a member named
‗Perry Paine‘.

He would issue the following SELECT statement.


       SELECT *
       FROM Member
       WHERE cFirstName=‗Perry‘
       AND cLastName=‗Paine‘;


But, if the library has more than one member with the name ‗Perry Paine‘, how
would the Oracle server be able to distinguish between them? This can be achieved
by giving each member a distinct identity number so that they could be identified
uniquely. This is achieved by defining the PRIMARY KEY constraint.

PRIMARY KEY constraints can be defined at the column level or at the table level.

To define PRIMARY KEY constraint at the column level for the Member table.


       CREATE TABLE Member
       (cMemberID CHAR (9) CONSTRAINT
        MemID_PK PRIMARY KEY,
        cFirstName CHAR (20) NOT NULL,
        cLastName CHAR (20) NOT NULL,
        vAddress    VARCHAR2 (50) NOT NULL,
        cArea      CHAR (10) NOT NULL,
        cZipcode   CHAR (7) NOT NULL,
        cPhone     CHAR (10),
        nAge       NUMBER (2) NOT NULL,
        dMembershipDt DATE,
        cGrade     CHAR (1),
        cBranchID CHAR(7));

© SQL Star International Ltd.                                                       300
In the code, the PRIMARY KEY is defined at the column level for the column
cMemberID. This constraint ensures that, when a row is inserted in the Member
table, the value for cMemberID column is a non-null value and is not same as an
existing column value of another row.




The FOREIGN KEY Constraint

A FOREIGN KEY constraint is defined on the column of a child table, which is
dependent on the primary key column of the parent table. Defining a FOREIGN KEY
constraint on a column or a collection of columns establishes a relationship between
the foreign key columns and the primary key or unique key columns of the same
table or a different table. This constraint ensures that foreign key columns do not
contain values that do not exist in the primary key column, they are referencing.
FOREIGN KEY constraints can be defined at the column level or at the table level.

The foreign key constraint is defined at the table level using the following keywords:

       FOREIGN KEY specifies the foreign key column in the child table.
       REFERENCES identifies the column in the parent table that the foreign key
       column is dependent on.
       ONDELETE CASCADE indicates that when a row in the parent table has
       been deleted, its dependent rows in the child table are also deleted.
         ON DELETE SET NULL converts foreign key values to null when parent
       value is removed. But, without the ON DELETE CASCADE and ON DELETE SET
       NULL, you cannot delete rows from the parent table if there are dependent
       rows in the child table.


For example, there exists a parent-child relationship between the Book table and the
Transaction table. The Transaction table contains the issue details of those books
that are listed in the Book table. The foreign key constraint is defined on the
cBookID column of the Transaction table (child table or dependent table). It refers
to the cBookID column of the Book table (parent or referenced table), which is the
primary key column.

To ensure that the books issued to members are those that are available in the Book
table of the library, create the Transaction table as follows:



© SQL Star International Ltd.                                                      301
CREATE TABLE Transaction
       (cTranID   CHAR(11) CONSTRAINT TransactionTranIDPK PRIMARY KEY,
        cMemberID CHAR(7),
        cBookID   CHAR(13),
        dIssueDt DATE,
        dReturnDt DATE,
        dActualReturnDt DATE,


       nFine NUMBER(2),
       CONSTRAINT TransactionBookIDFK FOREIGN KEY(cBookID)
       REFERENCES Book(cBookID)ON DELETE CASCADE,
       CONSTRAINT TransactionMemberIDFK FOREIGN KEY(cMemberID)
       REFERENCES Member(cMemberID)ON DELETE CASCADE);


When the FOREIGN KEY constraint is defined at the column level, there is a slight
change in the syntax. The FOREIGN KEY keyword is not used while defining it.

The following example illustrates this:

Define a constraint on the Availability table to ensure that it stores the status of
availability of only those books that are stored in the library.


       CREATE TABLE Availability
       (cBookID CHAR(13) CONSTRAINT AvailabilityBookIDFK

       REFERENCES Book (cBookID),
       nAvailableCopies NUMBER (2),
       cBranchID CHAR (7) CONSTRAINT AvailabilityBranchIDFK
       REFERENCES Branch (cBranchID));

In the code, the FOREIGN KEY constraint has been defined at the column level for
both cBookID column and cBranchID column.




© SQL Star International Ltd.                                                   302
The CHECK Constraint

The CHECK constraint ensures that the data being entered into a column satisfies a
set of valid values or conditions. For instance, it is the New Jersey Central Library‘s
policy not to allow any person below the age of five to be registered as its member.
Hence, if the librarian inserts a row into the Member table entering a member‘s age
as four, then the Oracle server would return an error saying that the CHECK
constraint for the nAge column has been violated.




To check whether the age of persons being entered in the Member table is not
below five, issue the constraint as follows:


       CREATE TABLE Member
       (cMemberID CHAR (9) CONSTRAINT MemberMemberIDPK PRIMARY KEY,
           cFirstName CHAR (20) NOT NULL,
           cLastName CHAR (20) NOT NULL,
           vAddress VARCHAR2 (50) NOT NULL,
           cArea CHAR (10) NOT NULL,
           cZipcode CHAR (7) NOT NULL,
           cPhone CHAR (10),
        nAge NUMBER (2) CONSTRAINT MemberAgeCK CHECK (nAge >5) NOT
       NULL,
           dMembershipDt DATE DEFAULT SYSDATE,
           cGrade CHAR (1)
           cBranchID CHAR(7) REFERRENCES Branch(cBranchID));


In the code, the CHECK constraint is defined for the nAge column, which ensures
that the age being entered is not below five.

Points to remember:

        While defining CHECK constraints, reference to columns or rows of any
       table, including the one on which the constraint has been defined cannot be
       made.
       For example, to check whether the publisher IDs entered in the Book table is
       among the publisher IDs specified in the PublisherDetails table you would
       type:


       CREATE TABLE Book
       (cBookID      CHAR(13) CONSTRAINT BookBookIDPK PRIMARY KEY ,
       cBookName       CHAR(20) NOT NULL,

© SQL Star International Ltd.                                                      303
cAuthorName CHAR(30) NOT NULL,
       cCategoryID CHAR(5) CONSTRAINT BookCategoryIDFK


      REFERENCES Category(cCategoryID) ,
      cPublisherID CHAR(6) CHECK (cPublisherID IN (SELECT cPublisherID
                                                             FROM Publisher)),
      dPublishedYr DATE,cBranchID CHAR(7)CONSTRAINT BookBranchIDFK
      REFERENCES Branch(cBranchID),
    nNoOfCopies NUMBER(2) CONSTRAINT BookNoOfCopiesCK
      CHECK(nNoOfCopies < 11));

However, this code is not valid as it refers to the cPublishedID column of the
PublisherDetails table and it displays the following error message:

      ORA-02251: subquery not allowed here

      References to functions such as SYSDATE, USER, etc. cannot be made
      while defining a CHECK constraint.

      MultipleCHECK constraints can be defined for a single column. CHECK
      constraints can be defined at column level or table level. Execute the
      following code to check whether the number of copies of books entered in the
      Availability table is not more than 5.


      CREATE TABLE Availability
      (cBookID CHAR(13) CONSTRAINT AvailabilityBookIDFK
      REFERENCES Book (cBookID),nAvailableCopies NUMBER (2),
      cBranchID CHAR(7) CONSTRAINT AvailabilityBranchIDFK
      REFERENCES Branch(cBranchID), CONSTRAINT AvailabilityCopiesCK
      CHECK(nAvailableCopies < 5));


In the code, the CHECK constraint on nAvailableCopies column has been defined at
the table level.




© SQL Star International Ltd.                                                  304
Consider an example shown below:

                        CREATE TABLE Emp
              (
              Empcode NUMBER(6),

                              Ename VARCHAR2(20)CONSTRAINT chk_ename
                              CHECK(ename=UPPER(ename)),
              Job_ID VARCHAR2(10) NOT NULL,
              Email VARCHAR2(40) UNIQUE,
              CONSTRAINT empid_pk PRIMARY KEY (Empcode)
                   );

In the above example empid_pk is a constraint defined as a primary key in the table
level for the column empcode.
The above example can be modified as:
          CREATE TABLE Emp


          (
    Empcode NUMBER(6) CONSTRAINT empcd_pk PRIMARY KEY,
    Ename           VARCHAR2(20),
    ...
                  Job_ID VARCHAR2(10) NOT NULL

© SQL Star International Ltd.                                                  305
);




Manipulating Tables using Constraints
If there are changes to the business rules, then changes to the constraints that
enforce these rules need to be made. These changes could include adding, removing,
disabling or enabling constraints.
Adding Constraints

Even when business rules have not been finalized, the database developers create
the tables so that, later the rules could be added to the columns or the tables of the
database. The syntax for adding a constraint is,


         ALTER TABLE <table_name>
         ADD [CONSTRAINT <constraint_name>] constraint_type (<column_name>);
Where,

table_name is the name of the table

constraint_name is the name of the constraint. The constraint name syntax is
optional.

constraint_type specifies the type of constraint to be added.

column_name is the name of the column to which constraint is to be added.

For instance, the library has not decided the rule pertaining to the eligibility of a
person to be registered as a member. The developer still creates the Member table.
Later, when the library management decides that only persons above the age of five
should be enrolled as members, this rule could then be incorporated in the Member
table which is already created.
         ALTER TABLE Member


         ADD CONSTRAINT MemberAgeCK CHECK (nAge < 5);


By adding this constraint, only the subsequent ages entered after the addition of the
constraint will be checked.

Another case where you need to alter a constraint is to add a constraint to ensure
that the grades allotted to each member in the Member table belongs to one of the
grades decided upon on the basis of age range in the MemberFee table.


         ALTER TABLE Member
© SQL Star International Ltd.                                                     306
ADD (CONSTRAINT MemberGradeFK FOREIGN KEY (cGrade)
       REFERENCES MemberFee (cGrade));


In the code, FOREIGN KEY constraint is added to establish a parent-child relation
between the Member table and the MemberFee table by ensuring that the grade
values in the Member table correspond to the grade values in the MemberFee
table.

Points to remember while adding constraints:

The column to which the constraint is to be added must already exist in the table.

PRIMARY KEY constraints: The columns must not have null values and must
have
     only unique values.

FOREIGN KEY constraints: The columns must have values corresponding to
values
       in the referenced primary key column or be null.

UNIQUE constraints: The column must have either unique values or be null.

CHECK constraints: Apply only to the subsequent data added to the
column.

NOT NULL constraints: These constraints can only be defined at column
level.      NOT NULL constraints are added using the MODIFY clause in the
ALTER TABLE      statement.

Deferred Constraints
Normally, constraints are checked as data is inserted or updated in the row. When a
row is inserted, all the constraints are checked and then, the row is either accepted
or rejected. You can, however, defer the constraint checking until the transaction
commits. In that case, the row is inserted into the table and constraints are not
checked until the COMMIT is issued. If the row then fails, it is removed from the
table. You can change the status of the constraints by setting them as DEFERRED or
IMMEDIATE. In order to change the constraint, it must be set to DEFERRABLE.




Consider an Example for using Deferred Constraints:


       CREATE TABLE Dupemp
       (Empno NUMBER(4) CONSTRAINT pk_empno PRIMARY KEY,
       Name VARCHAR2(20),
       Deptno NUMBER(2)


© SQL Star International Ltd.                                                    307
);


       CREATE TABLE Dupdept
       (Deptno NUMBER(2) CONSTRAINT dp_pk PRIMARY KEY,
       Dname    VARCHAR2(20),
       Loc    VARCHAR2(20));


If you try to enter values into Deptno column of Dupemp table, which does not lie
within the domain of the column values of Dupdept table, an error message is
thrown indicating the violation of foreign key constraint.


But, if you still want to add data into the Dupemp table, you can do it by changing
the status of the constraints by setting them as DEFERRED or IMMEDIATE. The
advantage of doing this is it defers constraint checking until the transaction is
committed. In order to change the constraint, it must be set to DEFERRABLE.


       ALTER TABLE Dupemp
       ADD CONSTRAINT dep_fk FOREIGN KEY(deptno) REFERENCES
       dupdept(deptno)
       ON DELETE CASCADE DEFERRABLE;


       SQL> SET CONSTRAINT dep_fk DEFERRED;


Now, you insert values into detpno of Dupemp table directly without entering the
corresponding deptno value in the main table.
As an example, the above one works perfect. But, why at all we need a deferred
constraint?
Sometimes, it so happens that, we get the data for the secondary table, but not for
the main table. Since there is a referential integrity constraint present on these two
tables, we cannot enter data directly into the second table.
By deferring the foreign key constraints, we can atleast get the data loaded into the
secondary tables, and then validate the data against the main table once it is also
loaded. This saves time. When a COMMIT statement is issued against the secondary
table, constraints are checked and invalid data is rejected.


We can enable the deferred constraint by issuing the following command:


        SQL> SET CONSTRAINTS dep_fk IMMEDIATE;

Dropping Constraints

If the organization decides to do away with a business rule, then you will have to
drop the constraint that enforced the rule. Use the DROP clause with the ALTER
TABLE statement to remove a constraint. The syntax for dropping a constraint is:

© SQL Star International Ltd.                                                       308
ALTER TABLE <table_name>
         DROP PRIMARY KEY | UNIQUE (column_name)|
         CONSTRAINT constraint_name [CASCADE];


Where,

PRIMARY KEY | UNIQUE (column_name)| specifies the primary key or the unique key
columns of a table that are to be dropped.

CASCADE option causes the dependent constraints to be dropped when the primary
key or unique key constraints are dropped.

Drop the primary key constraint from the Book table along with its associated
foreign keys.


         ALTER TABLE Book
         DROP PRIMARY KEY CASCADE;


In the code, the CASCADE option used with the DROP clause causes the dependent
constraint on cBookID columns of Transaction table and Availability table also to
be dropped.


Enabling and Disabling Constraints

Rectifying a constraint failed during creation is similar to the way any electric gadget
would be repaired. To repair an electric gadget you would first of all see to it that the
electric supply has been switched off until the repair work has been completed.

Likewise, to repair a failed constraint you must first switch off or in technical terms
disable the constraint and after taking steps to rectify the failure, switch on or enable
it.
Disabling Constraints

The Oracle server automatically disables a constraint that has failed during creation.

A simple example to explain this task. Create two tables Tab1 and Tab2.


         CREATE TABLE TAB1
         (nCol1 NUMBER (4) CONSTRAINT TAB1nCol1PK PRIMARY KEY,
         cCol2 CHAR (4));


         CREATE TABLE TAB2
         (cColA CHAR (4),nCol1 NUMBER (4) CONSTRAINT TAB2nCol1FK
         REFERENCES TAB1 (cCol2));
© SQL Star International Ltd.                                                        309
In the above codes, the primary key constraint is defined on the column nCol1 of
Tab1. The foreign key constraint is defined on the column nCol1 of Tab2. But the
creation of this constraint fails as it references cCol2 of table Tab1 instead of
nCol1. This automatically disables the Tab2nCol1FK constraint. The error message
displayed is as follows:

         ORA-02267: column type incompatible with referenced column type

In the above case, the constraint was disabled automatically as its creation failed.
However, you can disable the constraint without dropping or re-creating it if you do
not want to enforce the rules defined for it. Using the DISABLE clause with the ALTER
TABLE statement can disable a constraint. Disabling a constraint renders it
ineffective, as if it had been dropped. The syntax for disabling a constraint is:


         ALTER TABLE <table_name>
         DISABLE CONSTRAINT <constraint_name> [CASCADE];




Where,

table_name is the table name

constraint_name is the constraint name

CASCADE option disables a dependent constraint if its primary key constraint is
disabled.

For example you can disable the unique key constraint defined on cBranchName
column of the Branch table.


         ALTER TABLE Branch
         DISABLE CONSTRAINT BranchBranchNameUK;


In this example you did not have to issue the CASCADE clause because the disabled
constraint did not have any dependent constraints. An example where you will have
to issue the CASCADE clause is to disable the primary key constraint defined on the
cBookID column of the Book table.


         ALTER TABLE Book
         DISABLE CONSTRAINT BookBookIDPK CASCADE;


This example uses the CASCADE clause because disabling the constraint on
cBookID column will affect the cBookID column constraint of the Transaction
table.


© SQL Star International Ltd.                                                    310
Points to remember:

        You can use the DISABLE clause with both the CREATE TABLE as well as
              the ALTER TABLE statements.

        Ensure that  data being entered, while disabling of a constraint, does not
              violate the rule that had been defined. If such a precaution is not taken,
              then enabling the constraints later will not be a smooth process.

Enabling Constraints

You must enable the disabled constraints after you have taken the steps needed to
correct the reasons that led to the failure of constraints during their creation. When
constraints are enabled the business rules that were defined would be enforced. The
syntax for enabling constraints is:


        ALTER TABLE <table_name>
        ENABLE CONSTRAINT <constraint_name>;


Where,

table_name is the table name

constraint_name is the constraint name

Points to remember:

You
              can enable only those constraints which have been defined and which
are currently disabled.

When you attempt to enable a disabled constraint, ensure that the data
that had been loaded into the table does not violate the rule that had been defined.
This is because when you enable a constraint, that constraint applies to all the data
in the table.

You can use the ENABLE clause with both the CREATE TABLE as well as the
ALTER TABLE statements.

The disabled UNIQUE KEY constraint of the Branch table can be enabled as follows:


        ALTER TABLE Branch
        ENABLE CONSTRAINT BranchBranchNameUK;


In this code, the disabled unique constraint is enabled. But, if duplicate branch
names had been entered during the time the constraint was disabled, then the above
code would not execute and would display the following error:
© SQL Star International Ltd.                                                         311
ORA-0229: cannot enable constraint BranchNameUK – duplicate keys found

To enable the primary key constraint defined on the cBookID column of the Book
table, execute the following statement:


         ALTER TABLE Book
         ENABLE CONSTRAINT BookBookIDPK;


In this code, the disabled primary key constraint is enabled.

But, if duplicate book IDs or null values had been entered during the time the
constraint was disabled, then the above code would not execute and would display
the following error:

         ORA-02298: cannot enable constraint BookBookIDPK –parent keys not
found

Cascading Constraints

While dropping columns you need to handle,

The
             referential integrity constraints that depend on the primary key or
unique key constraints defined on the columns that are to be dropped.

All
            multicolumn (a single constraint which defines rules for two or more
columns) constraints defined on the columns that are to be dropped.

Example of a multicolumn constraint is:

         CONSTRAINT Constraintname CHECK (Col1 > 10 AND Col2 = 25)

The above-mentioned issues are handled by using the CASCADE CONSTRAINTS
clause along with the DROP COLUMN clause in the ALTER TABLE statement. Its
syntax is:


         ALTER TABLE <table_name>
         DROP COLUMN (<column_name>) CASCADE CONSTRAINTS;


For example create a table TabA.


         CREATE TABLE TabA
         (nC1 NUMBER (4)PRIMARY KEY,
          nC2 NUMBER(3),
          nC3 NUMBER (3),




© SQL Star International Ltd.                                                312
nC4 NUMBER (4),
       CONSTRAINT TabAnC4FK FOREIGN KEY (nC4) REFERENCES TabA (nC1),
       CONSTRAINT TabACK1 CHECK (nC3 > 10 AND nC2 <5));


The table TabA is created with four columns nC1, nC2, nC3 and nC4. Primary key
constraint is defined on column nC1 which is referenced by the foreign key column
nC4. A multicolumn CHECK constraint is defined on columns nC2 and nC3.

When you attempt to drop the columns nC1 and nC3, you would encounter error
messages.


       ALTER TABLE TabA
       DROP COLUMN (nC1);


Executing this statement would give the following error:

       ORA-00904: invalid column name

This is because nC1 is being referenced by nC4.

If you drop column nC3


       ALTER TABLE TabA
       DROP COLUMN nC3;


Executing this statement would give the following error:

       ORA-12991: column is referenced in a multi-column constraint

This is because nC3 is part of the multicolumn constraint.

To avoid these errors, use the CASCADE CONSTRAINTS clause with the DROP
COLUMN clause. Hence drop the columns as follows:


       ALTER TABLE TabA
       DROP COLUMN nC1 CASCADE CONSTRAINTS;


       ALTER TABLE TabA
       DROP COLUMN nC3 CASCADE CONSTRAINTS;



If the columns referencing the constraints of the dropped columns are also dropped,
then you need not use the CASCADE CONSTRAINTS clause with the DROP COLUMN
clause.

© SQL Star International Ltd.                                                  313
For instance in the same example you drop columns C1 and C4                 without the
CASCADE CONSTRAINTS clause.


       ALTER TABLE TabA
       DROP (nC1, nC4);
Querying USER_CONSTRAINTS Data Dictionary View

You can confirm the creation of a table by issuing the DESCRIBE command. But,
except the NOT NULL constraint, the DESCRIBE command does not verify the
existence of other constraints that were defined during the creation of the table.
Therefore, you can query the USER_CONSTRAINTS dictionary view to confirm the
creation of all the constraints on your table.

Before you query USER_CONSTRAINTS, issue the DESCRIBE command to see all the
columns that are available in it.

       DESC USER_CONSTRAINTS

Now, query USER_CONSTRAINTS using the SELECT statement to display all the
constraints defined on the Member table.


       SELECT CONSTRAINT_NAME,CONSTRAINT_TYPE,SEARCH_CONDITION
       FROM USER_CONSTRAINTS
       WHERE TABLE_NAME=‘MEMBER‘;


Displays the output:


       CONSTRAINT_NAME             CON          SEARCH_CONDITION
       --------------- ---------         -------------------------
       SYS_C001297                                  C                ―CFIRSTNAME‖      IS
       NOT NULL
       SYS_C001298                          C               ―CLASTNAME‖ IS NOT NULL
       SYS_C001299                          C               ―VADDRESS‖     IS NOT NULL
       SYS_C001300                          C               ―CAREA‖      IS NOT NULL


       SYS_C001301                          C               ―CZIPCODE‖ IS NOT NULL
       MEMBERAGECK                          C               nAge > 5
       MEMBERMEMBERIDPK                     P
       MEMBERGRADEFK                        R


       8 rows selected.

© SQL Star International Ltd.                                                       314
In the code, you are retrieving the name of the constraint, the type of constraint and
the search conditions used with the check constraints. If the user has not named the
constraints, then the query retrieves the names assigned by the server. In the type
of constraints retrieved by the code, C stands for CHECK and NOT NULL, P for
PRIMARY KEY, R for FOREIGN KEY and U for UNIQUE KEY.




Querying USER_CONSTRAINTS does not retrieve the columns on which the
constraints have been defined. In order to view the columns associated with the
constraints use the USER_CONS_COLUMNS data dictionary view. This view is
especially useful when system assigned constraints names have been retrieved by
USER_CONSTRAINTS, because these names do not help in identifying the columns
on which they have been defined. You can identify the columns associated with the
constraints by viewing the USER_CONS_COLUMNS data dictionary view.

The usage of USER_CONS_COLUMNS dictionary view is most widely felt when you
have to drop constraints from a table.

To drop a constraint, you need to identify the name of the constraint that is to be
dropped. By viewing USER_CONS_COLUMNS dictionary view, you can identify the
constraint names and columns on which they have been assigned and then use it in
the
DROP CONSTRAINT clause.

Display the constraints along with columns on which they have been defined on the
Member table.


       SELECT CONSTRAINT_NAME,COLUMN_NAME
       FROM USER_CONS_COLUMNS


       WHERE TABLE_NAME=‗MEMBER‘;


Displays the output:


       CONSTRAINT_NAME                 COLUMN_NAME
       -------------- --------------
       MEMBERAGECK                                  NAGE
       MEMBERGRADEFK                   CGRADE
       MEMBERMEMBERIDPK                CMEMBERID
       SYS_C001297                     CFIRSTNAME

© SQL Star International Ltd.                                                     315
SYS_C001298                  CLASTNAME
       SYS_C001299                  VADDRESS
       SYS_C001300                  CAREA
       SYS_C001301                  CZIPCODE
       8 rows selected.



Summary

In this chapter, you have learnt that:
         Data accuracy and consistency can be checked by creating constraints in
          database.
          Constraint can be defined before or after the table creation. These are
          defined        either at the table level(after defining all the columns) or at
          the column level(after        each column).
         The different types of constraints are: NON NULL: defined only at column
          level and      prevents NULL values, UNIQUE: prevents duplicate values,
          PRIMARY KEY: prevents               duplicate and NULL values, FOREIGN
          KEY: values referred by PRIMARY KEY domain             columns      only,
          CHECK: allows values based on a criteria.
         You can defer the constraints till the transaction commits using DEFFERED
          statement.
         Constraint can be either created, dropped, enabled or disabled using
          ALTER statements.
         Information regarding Constraints can be viewed in USER_CONSTRAINTS
          and           USER_CONS_COLUMNS data dictionary respectively.




© SQL Star International Ltd.                                                       316
Lab Exercise

1.     Add a table level PRIMARY KEY constraint to the new_emp table on the
       empID column. Name the constraint as emp_id_pk. [Hint: Use the ALTER
       TABLE command].

2.     Create a table NEW_DEPT with columns for department ID, department
       name and location ID. Create primary key constraint to the NEW_DEPT table
       using the deptID column. Name the constraint deptID_pk.

3.     Add the column deptID to the NEW_EMP table. Add a foreign key constraint
       on the NEW_EMP table using the deptID column. This ensures that the
       employees are not assigned to a department that does not exist. Name the
       foreign key constraint as emp_dept_fk.

4.     Confirm that the constraints are added by querying the USER_CONSTRAINTS
       view.




                     -------------

                     7 rows selected.



5. Create a table dept_Details based on the following details.




6.            Create a table emp_details based on the following chart.


© SQL Star International Ltd.                                               317
A)    Modify the emp_details table to add the foreign key on department id column.
      Also ensure that this constraint can be deferred.
B)    Make Necessary changes to make the constraint deferred.
C)    Insert 1 record into emp_details table first.
D)    Will it raise an error during inserting? If no, then why?
E)    Try to commit the inserted data. Is the data committed? If no, why?




© SQL Star International Ltd.                                                 318
Chapter 14




                                                     Views

                                               What are     Views
                                     Simple vs Complex      Views
                                Enforcing Constraints on    Views
                                       Creating Complex     Views
                                          Creating Inline   Views
                                       Data Access from     Views




© SQL Star International Ltd.                                 319
Objectives

   At the end of this chapter, you will able to:

     Describe the need for different types of views

    Use views




© SQL Star International Ltd.                          320
What are Views?
A view is defined as a database object that allows you to create a virtual table, which
would contain data selected from a table or a collection of tables and presented in a
distilled form to conceal complexity. The tables on which views are based are known as
base tables or underlying tables.

Views can be compared to windows; windows that only give you a glimpse of the
world surrounding you, concealing all its complexities. For example, consider the
view residents living in a tall building like Majestic Towers would get. When person
P1, living on the first floor looks out of his window, he probably gets to see nearby
buildings like a bank, a hospital and some people going on with their daily activities.
But when person P2, living on the top floor looks out of his window, the view he gets
would differ from that of person P1. For instance, in addition to the buildings and
people, he could also get a glimpse of trains plying from a near by station. This
shows that each window shows a different view of the same landscape surrounding
Majestic Towers. Similarly, VIEWS too present different views of the same table to
different users.

What the residents get to view from their windows does not belong to them.
Similarly, views too contain no data of their own. Views are just results of SELECT
statements. Therefore, when users manipulate data from views it is similar to
manipulating data from a table.

Why Views?
Views are widely used due to the following reasons:

      Views provide security as they can restrict data being accessed by users. For
        example, to implement data security, the library may create a view that will
        allow the librarian to see only the details of the library‘s members, thus,
        preventing him from manipulating data pertaining to the books, or the
        membership fee structure of the library.

      Views conceal data complexity by making complex queries simple. For
        example, retrieving data from two or more tables using a JOIN statement
        could prove to be very confusing for an end user. To simplify this complexity,
        you could create a view, which is a combination of two or more tables. For
        example, you could create a view by combining the Book, Category and
        PublisherDetails tables, thereby enabling the end user to make a simple
        query on the view without ever having to know that it is based on these three
        tables.

      View definition remains unaffected despite any alteration to the structure of
        its base tables (except when the tables are dropped or the table columns
        selected by the view is altered). For example, if a view were made of two
        tables, selecting two columns from one table and three columns from the
        other, adding one more column to the first table would not affect the view
        definition. Therefore, any application that refers to the view also remains
        unaffected.



© SQL Star International Ltd.                                                        321
   Data dictionary views are widely used as they prevent users from directly
        accessing the tables of the data dictionary. This is important due to the
        following reasons:

         To safeguard data stored in the data dictionary tables. If users manipulate
        data dictionary tables it could result in loss of data or the table itself being
        removed, thus causing serious damage to the Oracle database, even
        rendering it completely ineffectual or unproductive.

         Data stored within the data dictionary tables are hard to comprehend.
        Therefore, dictionary views help to condense data into something easily
        comprehensible and helpful.

Simple Views Vs Complex Views
Views can be classified into two types depending on the need for which they are to
be created. They are:

      Simple views

      views Complex


The basic differences between simple and complex views are:

      Simple views are based on only one table whereas complex views are based
        on more than one table. For example, the database developer could create a
        simple view based on the Book table. Whereas, he could create a complex
        view to show the books that belong to each category by joining the Book
        table and the Category table.

      Simple views allow DML operations to be performed (but with certain
        restrictions) whereas complex views do not always allow DML operations to
        be performed.

                       The syntax for creating simple as well as complex view is the
                       same except that the subquery that defines a simple view
                       cannot have any join conditions or group functions.




Creating Views
To create a view, a subquery must be embedded within the CREATE VIEW
statement. The syntax for creating a view is:

        CREATE [OR REPLACE] [FORCE| NOFORCE] VIEW <view_name> [(alias [,
        alias]…)]

© SQL Star International Ltd.                                                       322
AS subquery
        [WITH CHECK OPTION [CONSTRAINT <constraint_name>]]
        [WITH READ ONLY];

                      Where,

                      OR REPLACE changes the definition of a view without dropping
                      or re-creating it.

                      FORCE forces the creation of a view even without the existence
                      of a base table.

                      NOFORCE this is the default option. It creates a view only if
                      the base table exists.

                      view_name is the name given to the view that is created.

                      alias specifies the names for the expressions which will hold the
                      values of the columns selected by the subquery.

                      subquery is the SELECT statement which retrieves the columns
                      that the view must have.

                      WITH CHECK OPTION is a type of CHECK constraint, which
                      specifies that only those rows that are selected by the view can
                      be inserted, updated or deleted.

                      CONSTRAINT constraint_name assigns a name to the CHECK
                      OPTION constraint.

                      WITH READ ONLY prevents any DML operations from being
                      performed on the view.

                      Points to remember while creating views:

      The subquery can contain complex SELECT statements, that is, SELECT
        statements, which include joins and group functions.

      The subquery cannot contain an ORDER BY clause. Specify the ORDER BY
        clause while retrieving data from the view.

Creating Simple Views
Simple views are created by embedding a subquery that retrieves data only from a
single table, within the CREATE VIEW statement.


For example, in order to prevent the librarian of the ‗Randolph NJ Library‘ from
accessing or modifying the book details of other branches, the library database
developer creates a view that shows details of only those books that are stored in
the ‗Randolph NJ Library‘. In order to create this view the developer would have to
execute the following code:


© SQL Star International Ltd.                                                         323
CREATE VIEW vwRandolphBook
        As SELECT cBookID, cBookName, cAuthorName,
        cCategoryID, cPublisherID, dPublishedYr, nNoOfCopies
        FROM Book
        WHERE cBranchID = '04RANNJ' ;
        View created.


On executing the code, vwRandolpBook view gets created containing book details
of only the Randolph branch, which is identified by its ID ‗04RANNJ‘. The structure of
the vwRandolpBook view can be displayed by issuing the iSQL*Plus DESCRIBE
command.

        DESCRIBE vwRandolpBook




Enforcing Constraints on Views
The base tables have constraints defined on them that limit the kind of data that can
be entered or modified. The views that are based on them too have the same
restrictions.


In addition, special constraints can also be enforced on views. This is made possible
by using:

      The WITH CHECK option

      The WITH READ ONLY option

The WITH CHECK OPTION
This option protects data integrity and performs data validation checks by ensuring
that the data being changed is the data the view can select. It sees to it that any
inserts or updates being performed through the view do not create rows that the
view cannot select.


For example, due to the frequent enquiries made by its members regarding the
books stored



© SQL Star International Ltd.                                                     324
in the ‗Princeton‘ branch (which has been assigned an ID 05PRINJ), the library
database developer decides to create a view that will contain details about all the
books the ‗Princeton‘ branch stores. But, the developer must ensure that the
librarian accessing the view does not make any changes to the data stored. To
ensure this the following code must be executed:


       CREATE OR REPLACE VIEW vwPrincetonBks
       AS SELECT *
       FROM Book
       WHERE cBranchID=‗05PRINJ‘
       WITH CHECK OPTION CONSTRAINT PrincetonBkCK;
       View created.


The code creates a vwPrincetonBks view with the WITH CHECK OPTION clause. By
specifying the WITH CHECK OPTION constraint, any attempt made by the librarian to
manipulate the branch ID for any row in the view will fail.


For example, if the branch ID of the book were changed to ‗01ADLNJ‘, the view
would no longer be able to select that book and therefore the following DML
operation performed fails:
       UPDATE vwPrincetonBks
       SET cBranchID=‗01ADLNJ‘
       WHERE cBookID=‗FIC050003232‘;
Displays an error:
       Error at line 1:
       ORA-01402: view WITH CHECK OPTION where-clause violation

The WITH READ ONLY option
Using the WITH CHECK OPTION ensures that the DML operations being performed
are within the scope of the view, that is, DMLs are performed on rows that the view
can select. But, how to ensure that no DML operations are performed?


This can be ensured by using the WITH READ ONLY option. This option prevents any
DML operation from being performed on the view. If any attempt is made to perform
DMLs on any row in the view, the Oracle server will generate an error.
For instance, if the DBA creates a view for the clerk ‗Brad Riley‘, he needs to ensure
that ‗Brad Riley‘ does not write into the view. The following code will help:


       CREATE OR REPLACE VIEW vwHamiltonBks
       AS SELECT * FROM Book
       WHERE cAuthorName=‗Shakespear‘
       AND cBranchID=‗03HAMNJ‘
       WITH READ ONLY;
© SQL Star International Ltd.                                                     325
View created.

                        The view vwHamiltonBks is created by adding the WITH READ
                        ONLY option, which     prevents any DML operations from
                        being performed on it.

                        If ‗Brad Riley‘ attempts to delete any row from the view, he
                        encounters the following error:


        DELETE FROM vwHamiltonBks
        WHERE cBookName=‗Othello‘;
        Error at line 1:
        ORA-01752: Cannot delete from view without exactly one key-preserved table

                        Similarly, if he attempts to add or modify a row, the Oracle
                        server would generate the following error:


        UPDATE vwHamiltonBks
        SET nNoOfCopies=6
        WHERE cBookName=‗Othello‘;
        ERROR at line 2:
        ORA-01733: virtual column not allowed here




Rules for Performing DML operations
                        The user of a view can insert, update or delete data on the
                        underlying table if the creator of the view allows him/her to do
                        so. However, there are a few restrictions that apply when the
                        user of a simple view attempts to perform any DML operations:

      The user cannot insert, update or delete data on the underlying table, if the
        view itself cannot select that data. This happens if the WITH CHECK OPTION
        is used.

      The user cannot insert, update or delete data on the underlying table, if the
        subquery that defines the simple view contains:
                         
                              GROUP BY or ORDER BY clause
                              Any single-row or group function
                              The DISTINCT keyword
                              Columns defined by expressions such as nNoOfCopies
                               *2

      The user cannot perform any DMLs if any references to virtual or pseudo
        columns such as ROWID, CURRVAL, NEXTVAL and ROWNUM are made by the

© SQL Star International Ltd.                                                          326
subquery. Pseudo-column is not an actual column of any table but returns an
        Oracle generated value when selected.

      The user cannot perform any DMLs if the WITH READ ONLY option is used in
        the subquery.

      The user cannot add data into the underlying table if it‘s NOT NULL column is
        not selected by the subquery. For example, the librarian cannot insert data
        into the Book table if the vwRandolpBook view does not select the
        cBookID column. This is because cBookID is a primary key column implying
        that it cannot contain null values. (Remember that you are attempting to
        insert values directly into the base table through the view.)


Creating Complex Views
                        Complex views are created by embedding a subquery that
                        retrieves data from more than one table, in the CREATE VIEW
                        statement. In addition to joins, the subqueries can possibly
                        contain:

      Single-row as well as group functions

      References to pseudo columns

      GROUP BY clauses

                        Complex views are created for concealing complexities involved
                        in retrieving data such as the performance of joins or using
                        group functions to obtain the result set.

                        For example, members may request the librarian to provide a
                        list of all the books stored in the ‗Randolph NJ Library‘ branch
                        complete with their category names. To do so the librarian
                        would have to cross-check both the Book as well as the
                        Category tables. This proves to be quite taxing, especially if
                        queries of the similar kind increase. To overcome this, the
                        developer creates a view by joining the two tables. The librarian
                        then needs to only query this view without even knowing that it
                        is based on two tables. Executing the following code would
                        create the view:


        CREATE OR REPLACE VIEW vwRandolphBooks
        AS SELECT B.cCategoryID, C.cCategoryName, B.cBookID, B.cBookName,
        B.cAuthorName,B.dPublishedYr,B.nNoOfCopies
        FROM Book B,Category C
        WHERE B.cCategoryID=C.cCategoryID
        AND B.cBranchID=‘04RANNJ‘;
        View created.

                        On the execution of the code, a complex view gets created
                        wherein the subquery contains a join condition.

© SQL Star International Ltd.                                                        327
SELECT cCategoryName,cBookName
      FROM vwRandolphBooks;


      CCATEGORYNAME          CBOOKNAME
      -------------   ---------------
      Math            Aha! Gotcha: Paradoxes to Puzzle and Delight
      Children                             Amelia Jane is Naughty Again
      .....                  ..............
      .....                  ..............


      38 rows selected.

                      But, if the library clerk wants to know the total number of
                      copies of books of each category that the library stores, then
                      the above view would not serve the purpose. To do so, the
                      developer would have to create a view by executing the
                      following code:


      CREATE OR REPLACE VIEW vwBookCopies
      (Category,TotalCopies)
      AS SELECT C.cCategoryName,SUM(nNoOfCopies)
      FROM Book B,Category C
      WHERE B.cCategoryID=C.cCategoryID
      GROUP BY C.cCategoryName;
      View created.

                      On executing the code, a complex view vwBookCopies gets
                      created that contains a group function.

                      The clerk can display the contents of the view by executing a
                      SELECT statement.


      SELECT *
      FROM vwBookCopies;

                      The statement retrieves the following result set:


      CATEGORY               TOTALCOPIES
      ----------       ---------
      Archaelogy           25
      Children            136


© SQL Star International Ltd.                                                      328
Classic             92
      Computers                36
      Fiction             55
      History             52
      Humor                74
      Math                56
      Mechanical           31
      Mystery              83
      Non Fiction          58
      Psychology           40
      Romance                  59
      Science Fiction          45


      14 rows selected.




                    Complex views do not allow data to be added, changed or
                    deleted on the underlying table because of the join that is
                    performed. Therefore, it is not necessary to specify the
                    WITH READ ONLY option as complex views are already
                    considered to be read only.

                    N.B.:- This can be resolved by creating INSTEAD OF triggers,
                    which will be dealt in a later chapter.

Constraints on Views
                    One of the Oracle9i constraint enhancements has been with
                    regards to the ability to create primary and foreign keys on
                    views. Now, you can specify constraints on view columns.
                    However, view constraints are declarative only. That is, they
                    are not enforced by the Oracle database.

                    View constraints are subject to the following restrictions:

© SQL Star International Ltd.                                                     329
   Only unique, primary key and foreign key constraints can be specified on
        views.

      You cannot specify clauses like DEFERRED or DEFERRABLE because view
        constraints are not enforced.

      View constraints can be specified only in the DISABLE NOVALIDATE mode.

   

      Clauses such as USING INDEX, EXCEPTIONS INTO, or ON DELETE clause
        cannot be specified in view constraints.


Creating Inline Views
                       In addition to creating simple and complex views, you can also
                       create Inline Views.

                       Inline views are named subqueries (a subquery with an alias)
                       written in the FROM clause. The named subquery defines the
                       source of data for the main SELECT statement.
                       For example, the library clerk would be required to produce a
                       list of books whose number of copies stored is less than the
                       maximum number of copies of books stored in their respective
                       branches.

                       To produce the desired result, the developer would have to first
                       retrieve the maximum number of copies of books stored in each
                       branch.


        SELECT cBranchID,MAX(nNoOfCopies) MaxCopies
        FROM Book
        GROUP BY cBranchID;


        CBRANCH       MAXCOPIES
        ------    --------
        01ADLNJ          9
        02CHSNJ          9
        03HAMNJ              9
        04RANNJ          8
        05PRINJ          9

                       The developer would have to then cross check the query output
                       with the Book table in order to find out those books whose
                       number of copies stored is less than the maximum number of
                       copies of books stored in their branches.




© SQL Star International Ltd.                                                      330
The developer could instead write the above SELECT statement
                     as a subquery in the FROM clause of a main query as shown
                     next:


       SELECT B.cBookName Book,B.nNoOfCopies Noofcopies,B.cBranchID
       BranchID,C.MaxCopies ―Max Copies‖
       FROM Book B, (SELECT cBranchID,MAX (nNoOfCopies) MaxCopies


                       FROM Book GROUP BY cBranchID) C
       WHERE B.cBranchID = C.cBranchID
       AND B.nNoOfCopies < C.MaxCopies;

                     The query displays the following result set:


       BOOK                          NOOFCOPIES BRANCHI Max Copies
       ---------                --------       ------      --------
       Archaeology as Cultural History           6                    01ADLNJ   9
       Fractals Everywhere                 2               01ADLNJ       9
       ...............          ..         ...       . .
       173 rows selected.

                     In the code, the SELECT statement inside the parentheses is
                     used as one of the ―tables‖ in the query and is given an alias,
                     C. It is treated just as if it were a view. It is this named
                     subquery that is known as an inline view.

                     Writing the following join condition joins the Book table and
                     the inline view:


       …WHERE B.cBranchID = C.cBranchID…

This join condition produces the same output that you would get by cross checking
the result of the subquery manually with the Book table.




Oracle7 and Oracle8 did not allow the use of the ORDER BY clause within subqueries.
But since Oracle8i you can use the ORDER BY clause with inline views.

The following code will illustrate the use of the ORDER BY clause:

© SQL Star International Ltd.                                                        331
SELECT M.Name
       FROM (SELECT cFirstName||cLastName Name
           FROM Member
           ORDER BY Name) M;
The query displays the following result:


       NAME
       -----------------
       Andre                  Cobb
       Austin                 Dinsmore
       Bridgette              Wells
       Celena                 Stevenson
       Cresinda               Finch
       Darla                          Green
       Derian                 Bates
       Eveangela              Gammons
       Ferdinand              Swander
       ----------   -------
       21 rows selected.


                       The Inline view retrieves a sorted list of member‘s names by
                       concatenating their first names with last names. This inline
                       view defines the data source for the SELECT statement. The
                       execution of the code does not result in any error despite the
                       use of the ORDER BY clause.



                       The importance of using the ORDER BY clause in inline views
                       can be seen when you need to retrieve the n largest or smallest
                       values of a column.

Top-N Analysis
                       Top-N analysis or top-n queries are used to retrieve the n
                       largest or smallest values of a column.

                       For example, there may be queries to retrieve the ten most
                       recently registered members in the library or to retrieve the
                       four most senior members of the library. To retrieve the desired
                       results, you will have to use top-n queries. The syntax for
                       creating a top-n query is:



© SQL Star International Ltd.                                                       332
SELECT column_list, ROWNUM
       FROM (SELECT column_list
           FROM <table_name>
           ORDER BY Top-N_column)
       WHERE ROWNUM <= N;


                       Where the top-n query consists of:

   •   A subquery or an inline view which includes the ORDER BY clause to ensure
       that the results are retrieved in the desired order. Specifying the ORDER BY
       clause retrieves the top n smallest values of a column. In order to retrieve the
       top n largest values use DESC keyword along with the ORDER BY clause.

   •   An outer query that limits the number of rows that is to be retrieved. It
       comprises of:

           The ROWNUM pseudocolumn, which assigns successive values to each
     of the rows returned by the subquery, and

          The WHERE clause, which specifies the number of rows that are to be
     returned. The WHERE clause must use a < or <= operator.

                       The outer query limits the number of rows by WHERE ROWNUM <= N.


Using Top-N Queries
                       If the developer has to find out the four most recently
                       registered members of the library, he would have to issue the
                       following SELECT statement:


       SELECT ROWNUM ―NEW MEMBERS‖,M.Name, M.MembershipDt


       FROM (SELECT cFirstName||cLastName Name, dMembershipDt MembershipDt
       FROM Member
       ORDER BY dMembershipDt DESC) M
       WHERE ROWNUM <= 4;
                 In the code, the inline view M returns the names and the
                 membership dates from the Member table, which are sorted in
                 the descending order of the membership dates. The outer query
                 selects the pseudocolumn ROWNUM, which assigns sequential
                 values to the rows that are returned by the inline view. The
                 rows returned are limited by the             WHERE ROWNUM
                 <= 4 clause, which ensures that only four rows from the
                 resultant rows are displayed.


       NEW MEMBERS            NAME                MEMBERSHIP
       -------------   -----------------     ---------

© SQL Star International Ltd.                                                             333
1            Norbert    Cambell         03-MAR-01
      2                  Johna       Butler           19-SEP-00
      3           Eveangela       Gammons         10-APR-00
      4           Ferdinand   Swander                03-MAR-00




Using Views
                      The users using views find that accessing data from the views
                      is similar to accessing data from a table. They can even modify
                      or remove views just as they would do to a table.

Data Access from Views
                      Before you access data from a view, you need to confirm its
                      creation by querying the USER_VIEWS data dictionary table. In
                      order to display the contents of USER_VIEWS issue the
                      DESCRIBE command.
      DESCRIBE USER_VIEWS
      Name            Null?                   Type
      ---------       ---------               ---------
      VIEW_NAME               NOT NULL                    VARCHAR2(30)
      TEXT_LENGTH                                    NUMBER
      TEXT                                    LONG
      TYPE_TEXT_LENGTH                               NUMBER
      TYPE_TEXT                                      VARCHAR2(4000)
      OID_TEXT_LENGTH                                NUMBER
      OID_TEXT                                       VARCHAR2(4000)
      VIEW_TYPE_OWNER                                VARCHAR2(30)
      VIEW_TYPE                                      VARCHAR2(30)


© SQL Star International Ltd.                                                     334
USER_VIEWS data dictionary view displays the name of the
                      view as well as the view definition. The view definition is stored
                      in the dictionary table as SELECT statements. The text of the
                      SELECT statements is stored in a LONG column.

                      For example, the developer of vwRandolpBook view could
                      confirm its creation by viewing USER_VIEWS.


       SELECT *
       FROM USER_VIEWS;

                      When a user attempts to access data using a view, the Oracle
                      server retrieves the view definition from USER_VIEWS and
                      converts it into a similar query on the underlying table, thereby
                      retrieving data from the base table.

                      For example, when the librarian attempts to retrieve data using
                      vwRandolpBook view, he would issue the following SELECT
                      statement:


       SELECT *
       FROM vwRandolpBook;

                      On encountering the above statement, the Oracle server
                      retrieves vwRandolpBooks views definition from USER_VIEWS
                      data dictionary. The view definition on being retrieved would
                      be:


       SELECT TEXT
       FROM USER_VIEWS
       WHERE VIEW_NAME=‘VWRANDOLPHBOOK‘;
Displays:
       TEXT
       --------------------------------
       SELECT cBookID,cBookName,cAuthorName,
       cCategoryID,cPublisherID,dPublishedYr,nNoO

                      The Oracle server then converts the view query into a similar
                      query on the underlying base table and retrieves data from the
                      base table.

Modifying Views
                      There are situations when the developers of views are required
                      to make some modifications to the views.
                      The statement used to modify a view is the CREATE OR
                      REPLACE VIEW statement. On issuing a CREATE OR REPLACE
                      VIEW statement, the Oracle server overwrites the old

© SQL Star International Ltd.                                                       335
definition of the view with the new one by overlooking the error
                      that arises on encountering an already existing view with the
                      same name. The following code illustrates the use of the
                      CREATE OR REPLACE VIEW:

                      For example, the user of the vwRandolpBook view may
                      suggest the developer that more meaningful names be
                      assigned to the columns as they currently have the same
                      names as the columns of the underlying Book table. To do so
                      the developer would have to modify the view by specifying
                      column aliases.


      CREATE OR REPLACE VIEW vwRandolpBook
      AS SELECT cBookID BookId,cBookName BookName,cAuthorName Author,
      cCategoryID CatgID, cPublisherID PublisherID,
      dPublishedYr PublishedYr, nNoOfCopies Copies
      FROM Book
      WHERE cBranchID=‘04RANNJ‘;
      View created.

        In the code, the OR REPLACE option replaces the old version of the
        vwRandolpBook view with the new one. The execution of the above code
        controls the column names by
        specifying aliases in the subquery.

        The column aliases can also be specified in the CREATE VIEW clause. But
        they must be listed in the same order as the columns that are selected by
        the subquery. The following code will illustrate how to specify column
        aliases in the CREATE VIEW clause:


      CREATE OR REPLACE VIEW vwRandolpBooK
      (BookID,BookName,Author,CatgID,PublisherID,PublishedYr,Copies)
      AS SELECT cBookID,cBookName,cAuthorName,cCategoryID,
      cPublisherID,dPublishedYr,nNoOfCopies
      FROM Book
      WHERE cBranchID=‘04RANNJ‘;
      View created.

                      Just as there is the ALTER TABLE statement to modify the table
                      structure, similarly there is an ALTER VIEW statement available
                      in the Oracle SQL language. The syntax is:

      ALTER VIEW view_name;

                      But instead of being used to modify the view structure, it is used to recompile a
                      view that becomes invalidated either due to:


© SQL Star International Ltd.                                                                      336
   Change made to the definition of the underlying table

      Deletion of the underlying table


To rectify the invalidated view you must either recreate the underlying table and
issue the ALTER VIEW statement or modify the view by using the CREATE OR
REPLACE VIEW statement.

Removing Views
                        There may arise situations that would require the developer of
                        a view to remove it from the database.

                        The statement used to remove a view is the DROP VIEW
                        statement. Removing a view does not affect the table on which
                        it was based. Only the view definition is removed from the
                        database. The syntax for dropping a view is:

                                 DROP VIEW <view_name>;

                        Where,

                        view_name is the name of the view that is to be dropped

                        For example, the developer creates a view to display the
                        addresses of all the library members, based on the requirement
                        made by the librarian for the purpose of sending mails to them.
                        The developer executes the following code to create the view:


        CREATE OR REPLACE VIEW vwMemberAddress
        AS SELECT cFirstName,cLastName,vAddress,
        cArea,cZipcode
        FROM Member;
        View created.

                        After querying the vwMemberAddress view, the librarian
                        would be able to retrieve the addresses of members and
                        accordingly send mails to them.


        SELECT *
        FROM vwMemberAddress;




The query displays the following result:




        CFIRSTNAME CLASTNAME             VADDRESS          CAREA     CZIPCODE
© SQL Star International Ltd.                                                       337
--------    --------      -----------   --------   -------
      Austin          Dinsmore 41B, Cliftwood Avenue,       Allenbury NJ01956
                         Fourth Cross Rd
      Bridgette   Wells 65A, Maple Breeze Apts,      Ridgeland     NJ04352
                        Redford Township
      Celena Stevenson 19-22A, Free Gallop Villa,        Roxbury   NJ90231
                        Greenwich Hallway Rd
      Ferdinand Swander 909D, Sunrise Marble Apts,         Stanhope NJ12543
                         Springwood Lane
      ----------------------
      21 rows selected.

                      After sending mails, the librarian would no longer need to query
                      the view as his purpose has been met. Therefore, the developer
                      (on being told by the librarian) would decide to remove the
                      view from the database.

                      The developer of the vwMemberAddress view would execute
                      the DROP VIEW statement to drop the view.


      DROP VIEW vwMemberAddress;
      View dropped.


                      Execution of this code removes the vwMemberAddress view
                      from the database.




© SQL Star International Ltd.                                                     338
Summary

                    In this chapter, you have learnt that:

      Views are virtual tables based on the underlying database tables. They can
          be visualized as a window to a base table.

    Views provide restrictive access to the base table, hide the complexity of
        joining multiple tables and can provide specific information for different
        users.

    Views based on single table are known as simple views. DML operations can
        be perfomed on these views directly.

      Views based on Multiple tables are known as complex views. DML operations
          can be done on these views through triggers only.

    Views are created using CREATE VIEW statement and modified using
          CREATE OR REPLACE VIEW statement.

    Inline views are named subqueries (a subquery with an alias) written in
          the FROM clause. The named subquery defines the source of data for the
          main SELECT statement. TOP-N analysis can be performed using Inline
          view.

    Constraints can be applied on views using WITH CHECK options and READ
          ONLY clauses.

        Information regarding Views can be fetched using USER_VIEWS data
          dictionary view.




© SQL Star International Ltd.                                                        339
Lab Exercise
1.   Create a view vwDept50EmpDetails to display the following of employees
      belonging to department number 50:

           IDs

           First name and last names concatenated together and named as
             Employees

           Job IDs

           Salary

      Retrieve the contents of the view. The view should display the contents as
       shown below.




2.   Create a view vwDeptSalaryDetails to display the maximum, minimum, and
      average salaries of each department. The view should display the results as
      follows:




© SQL Star International Ltd.                                                      340
3.   Make the following modifications to vwDept50EmpDetails:

           Include the department number in the view

           Ensure that any attempt to reassign an employee to any other
             department through the view fails

      After making the modifications, try and update the department number of
      employee ID to 120. What error message do you get?

4.   Create a view vwEmpDetails, which should display the following:

           Employee first name and last name concatenated and given an alias
             Name

           Department name

           Job title

           City name

           Country name

           Region name

           Salary

Ensure that no DML operations can be performed on the view.

The view should display the result as shown below.




© SQL Star International Ltd.                                                   341
5   Retrieve the view name and view text of vwDept50EmpDetails,
      vwDeptSalaryDetails and vwEmpDetails views from USER_VIEWS data
      dictionary view.
      [Hint: For better readability, use the iSQL*Plus SET LONG n, where n is the
      number of characters of the LONG column you would want to see]

6.   Create an inline view to display the last name, department number, salary
      and average salary for all those employees who earn a salary less than the
      average salary in their respective departments.
      On querying the view, the following result should be displayed:




7.    Write a query to display the last names and salaries of the top 10 salary
      earners. The query should display the following result:




© SQL Star International Ltd.                                                   342
Chapter 15




                                Other Database Objects

                                                        Indexes
                                               Types of Indexes
                                                   B-Tree Index
                                                   Bitmap Index
                                           Working With Indexes
                                         Index Organized Tables
                                                      Sequences
                                                      Synonyms




© SQL Star International Ltd.                               343
Objectives


At the end of this chapter, you will be able to:

   State the need for Indexes

   Use Indexes

   Define the role of Sequences

   Use Sequences

   Use Synonyms

Indexes
When you request for a particular row of data, the server does a full table search and
when the requested row is found, it is retrieved and displayed. The process of full
table scan takes a lot of time and also uses up a lot of the system resources. To
quicken the process, you can create an index. An index is a database object with
which you can increase the speed of data retrieval.

Following are the uses of indexes:

    Indexes ensure that all data in a column with an index is unique.
    Indexes ensure faster retrieval of data.


Creation of Indexes
Indexes are created to enforce integrity constraints for uniqueness. Indexes are
created either:

    Automatically
    Manually

Automatic Creation

Automatic indexes are called so, because the Oracle server creates them. These
indexes are created when a table with a column having the primary key or the
unique key constraint, has been created. When the constraint and its supporting
index is created and the column values are put into it, the index takes its name after
the constraint. In case you do not name the constraint when creating the table, the
system gives the index a name like SYS_28349240. Automatic indexes are created
basically to enforce the uniqueness check. The difference between an index created
with the primary key and that with a unique constraint index is that the former does
not allow NULL values and the latter does.


© SQL Star International Ltd.                                                      344
There could be requirements in a database for indexes other than the ones that are
automatically created. These need to be created manually.

Manual Creation

Manual indexes are created using the CREATE INDEX statement. They are not
different from the indexes that are created automatically. The only way you can
differentiate an automatically created index from a manually created one is from its
name. You would follow some naming convention of your own to name the index you
create. For example, an index of a primary key in the Member table of the library
database could be called idxMemberPK. The Oracle server follows its own
conventions for naming indexes.

The syntax for creating an index is as follows: [This is not the complete syntax. It is
dealt in depth later in this topic.]


         CREATE INDEX <index_name>

         ON <table_name> (column[, column]…);


Where,

index_name is the name you assign to the index you are creating.

table_name is the name of the table whose column you are attempting to index.

column is the name of the column in the table you are trying to index.

You can create non-unique indexes to speed up the accessing of rows. For instance,
the library desk officer has to frequently query the Book table to retrieve books
based on their author names. To speed up the access time, the database developer
could create an index on the author name column using CREATE INDEX statement as
follows:


         CREATE INDEX idxAuthorName
         ON Book (cAuthorName);

On successful creation of the index, you get the following message:

         Index created.


Types of Indexes
The types of indexes available are:

       B-tree index
       Bit-map index
       Non Unique Index
       Compressed Index
       Function-based index
© SQL Star International Ltd.                                                      345
B-Tree Index

B-tree is the traditional index of the Oracle database and is based on a complex
algorithm of sorting. Data in a B-tree is stored in a top to bottom manner resembling
an inverted tree. This kind of data storage is based on the binary search tree
concept. The highest level of the data store is called the root-node and is depicted on
top of the inverted tree. The data is in a sort of a list and is arranged in a layered
and branching manner.


When the values are stored in this manner the data does not have to be searched in
a sequential manner, which is time consuming. It is suggested that data should be
stored in this manner when the column has many distinct values or when the column
is unique.

The B-tree consists of branch nodes, leaf nodes and data blocks.

The algorithm of a B-tree is as follows:

   1. Data is stored in the form of a list with the midpoint of the list as the root-
   node. Each section‘s midpoint is in turn made the next level and so on.

   2. The data to be searched is compared with the values at the midpoint. If the
   value is greater, then the values below the midpoint are eliminated. If the search
   value is lower than the midpoint value, the values above the midpoint are
   eliminated.

   3. This process is performed with every successive section and its midpoint, till
   the value is found.




© SQL Star International Ltd.                                                           346
Nodes store certain important information referred to as ROWID. This stores
information about the row location of the value on the disk. These are pointers to the
data values.
Data is stored in an order and the NULL values if any are not indexed. Multiple data
blocks are read at a time enabling faster scan of data. Rows of data are found by
traversing the branches of the tree and scanning the leaf blocks. If the search
required more columns, then the data block is accessed.




Let us take an example to understand B-Tree Index better.




From the above tree structure if we want to find the value of 45, we start from the
top of the tree and move towards the right. We would read the block and find that
we should go to the block in the range ‗less than 50 to 40‘. This block will be the leaf
block and point to the rows containing the number 45. Note that the blocks in the
leaf nodes are doubly linked. This would help us in solving range scans because all
we need to do is to identify where to ‗start‘ in the leaf node and once it‘s found doing
an ordered scan of values is very easy.
© SQL Star International Ltd.                                                       347
For example,

To solve the query,

       SELECT * from <table name>

       where x between 20 and 30;

Oracle will simply find the index block that contains 20 and from there the scanning
goes horizontally till 30. Here the advantage is that it does not have to navigate
through the entire tree structure again.

Bitmap
A bitmap index is structured like a matrix where the data value in a table column is
shown in columns along one axis of the matrix. The other axis contains the ROWIDs.
Every value is represented in one column; hence if a column in a table has too many
distinct values the index will become larger. Therefore, this kind of index is best
applied to a table where there are as few distinct values (also referred as low
cardinality columns) as possible.




Indexes are also classified as unique and non-unique depending on the data that
they store.




Consider the Member table in the Library example explained in this book. Two
columns are ideal candidates for bitmap index namely cMaritalstatus (Only Y/N) and
cGrade (A/B/C/D).

       MEMBERID            CGRADE           CMARITALSTATUS
       --------            -------          ----------------
© SQL Star International Ltd.                                                     348
CDB028504                 C                      N

      BAD109001                 B                      N

      CBW109702                 C                      Y

      ACS099903                 A                      N

      DFS030005                 D                      Y

      BKF079702                 B                      N

      CNC030103                     C                      N

      BLB089904                     B                      N

      ...........          ........                .........

      etc

Once the bitmap index is created on CMARITALSTATUS, Oracle will store
something like the following table.

                      Cmaritalstatus_bitmap_ind




Considering bitmap index being created for Cgrade the structure would be

                       Cgrade_bitmap_ind




© SQL Star International Ltd.                                              349
In the first row marital status is ‗N‘ so the bit ‗N‘ is ‗1‘, in the third row the marital
status is ‗Y‘ so the bit is ‗1‘ and the value for ‗N‘ is ‗0‘ so the bit is ‗0‘ and so on.

In the Bitmap index of cGrade, first row is ‗C‘ so the bit Corresponding is ‗1‘.
Similarly, in the 5th row, the value for grade is D; hence, it is equivalent bit in
column D is ‗1‘.

Consider a query,

       SELECT count(*)
       FROM Member
       WHERE cmarital status =‘ N‘ AND Cgrade IN(‗C‘,‘B‘);


 The above query involves the bitmap of ‗N‘, ‗C‘ and ‗B‘. While processing, the bitmap
‗N‘ ‗C‘ and ‗B‘ will be taken as

        ‘N’                            ‘C’                           ‘B’
                                                                           0
        1                             1
                                      0                                    1
        1
        0                             1                                    0
        1            AN               0             OR                     0
                                      0                                    0
        0
        1
                     D                0                                    1
        1                             1                                    0
        1                             0
                                                                           1


The result of ‗OR‘ operator combined with ‗AND‘ is calculated to fetch the final
resultant.




© SQL Star International Ltd.                                                            350
From the Bitmap result there are 5 records satisfying the condition, because there
are 5 ones (1) in the result set.




As discussed earlier, the server creates unique indexes automatically, when a column
of a table is set with the unique or primary key constraint. The structure of a unique
index is a B-tree.


Non-unique
The non-unique index is manually created on a column, which is most frequently
used for queries. The data in the column may contain duplicate values. This could be
an index on a foreign key column of a table.


Compressed Index


© SQL Star International Ltd.                                                     351
This type of index saves the disk storage by storing the repeated portion of the
column value (Key), just once, depending on the degree of compression. There are a
lot of real applications that can use this type of index effectively.

Consider an application which maintains a table for storing object details created for
an application like owner, object type and object name. Whenever new objects are
created it gets a new entry in the table. When application wants to retrieve that
information it can have a compressed index, which saves lot of space in the disk.

Considering the three columns mentioned above the data would be something like
this:


          SCOTT.TABLE.MYTAB
          SCOTT.TABLE.EMP
          SCOTT.TABLE.DEPT


          SCOTT.PROCEDURE.P1
          PROCEDURE.P2
          ....
    ...

An uncompressed index for the above data would be like the sample data above,
which is a concatenated index on all the three columns.

For a compressed index with a degree of compression ‗1‘ it will be


          CREATE INDEX myindex ON <tablename>(OWNER,OBJECTNAME,OBJTYPE)
          COMPRESS 1;

In this case the storage would be,




The above Index would definitly occupy less space ,since the key (username) is
stored only once.



© SQL Star International Ltd.                                                      352
Function-Based Index
Another kind of index is a function-based index. This index is created based on the
expression used in the SELECT statement or other DDL statements.

This query helps you to use the index to search for data rather than do an entire
table scan. To ensure this, you need to specify the WHERE clause with the condition
that the column of the values of the expression does not contain a NULL. If you do
not specify the clause, the server may scan the entire table.

For instance, the following query could have been implemented with a complete table
scan if the WHERE clause was not specified:


       SELECT * FROM Transaction
       WHERE nFine IS NOT NULL
       ORDER BY nFine;

Prior to Oracle9i, all the columns used in the function-based index had to be declared
NOT NULL. But from the 9i release, even if the expression contains a NULL value, the
built-in operators recognize them as NOT NULL and give a result that is NOT NULL.
Therefore, the function-based index will contain NOT NULL values and the index-only
scan can be performed on it.




© SQL Star International Ltd.                                                     353
Working with Indexes
Using an index involves creating it and following some guidelines to do so. There can
be some negative consequences if a table has too many indexes. You should be able
to manipulate the index and perform tasks related to maintaining all the indexes in a
database.



Creating an Index

The process of creating an index comes into picture when you need to create it
manually. Unique and primary indexes are automatically created by the system when
the respective constraints are set on table columns. These indexes can also be
manually created by using the CREATE INDEX statement. You need to specify the
type of index to be created with the CREATE INDEX statement. For instance, the
syntax to create a unique index is as follows:


         CREATE UNIQUE INDEX <index name>
         ON <table name> (column_name);

Where,

CREATE INDEX is the key word to create the index

UNIQUE is the keyword that specifies that a unique index is to be created

<index name> is a name for the index

<table name> is the table on which the index is to be created.

column_name is the name of the column on which the index has to be created

For example, for faster retrieval of data from the NonMember table, you can create
a unique index on the nSerialNo column as follows:


         CREATE UNIQUE INDEX idxNonMemSer
         ON NonMember(nSerialNo);
© SQL Star International Ltd.                                                    354
Index created.

You can also create an index:

    On more than one column thus creating a composite index
    Of bitmap type by using the BITMAP keyword instead of UNIQUE

However, creating an index is not very easy. You need to think about query
performance, database performance and size and requirement of the indexes to be
created. An index is needed to be created according to the requirements of a table.
You need to decide when to create a B-tree index and when to create a bitmap
index. If you create many indexes on a table it does not imply that the data retrieval
speed increases. On the contrary, any manipulations to the table data needs to be
reflected on the indexes and this could be a time taking process.

Some points to help you decide when it is best to create indexes are given below:

    A particular column (or columns) is frequently used in the WHERE clause of a
      SELECT statement or in a JOIN condition.
    The column holds a large range of values or a large number of NULLS.
   The table is of a large size and the result set of a query is less than 2-4 % of
   the rows in the table.

There are some cases, like the following, where creating an index may not prove to
be useful:

    If the table in question is small in size
    If the columns of a table are not frequently used in a query
    If the result set of a query is expected to be about 2-4 % of the rows in the
      table
    If the table requires frequent updates. In this case, every time the table is
      updated all the indexes on the table need to be updated too.



Altering an Index

You cannot make many changes to an existing index directly. If you want to change
the structure of an index, you need to first remove the index completely and
recreate it with the new specifications.

View Index Structure

You can check if there are any indexes that have been created. Whether created
manually or automatically, all indexes are stored in the database with their structure
definition. You can confirm the existence of the indexes in a database by using the
USER_IND_COLUMNS. The information stored in this data dictionary is the name of
the index, the column name on which the index is created and the table name.




© SQL Star International Ltd.                                                       355
The ALL_INDEXES data dictionary view contains information about the storage of
indexes. The names of the tables of the indexes are also stored. The USER_INDEXES
data dictionary view displays the names of indexes and the type of index it is (that
is, its uniqueness).

Using the data dictionary views, confirm the creation of your indexes.


       SELECT ic.Index_Name, ic.Column_Name, ic.Column_Position col_pos,
       ui.Uniqueness
       FROM USER_INDEXES ui, User_Ind_Columns ic
       WHERE ic.Index_Name = ui.Index_Name
       AND ui.Table_Name IN (‗NonMember‘,‘Book‘);

The above SELECT statement displays the following result:


       INDEX_NAME               COLUMN_NAME              COL_POS   UNIQUENES
       ----------       -----------   --------   ----------
       IDXAUTHORNAME            CAUTHORNAME              1    NONUNIQUE
       BOOKBOOKIDPK             CBOOKID          1            UNIQUE
       IDXNMEMSER                NSERIALNO           1        UNIQUE




Removing Indexes

Once indexes are created and if the users no longer require them, they can be
deleted. You can remove an index by using the DROP INDEX command. When an
index is dropped, it is removed from the data dictionaries and indexed searches are
no longer performed on the database. If the index was based on a constraint like
UNIQUE, then it will not enforce the constraint. The syntax for removing the index is:

       DROP INDEX <index_name>

The unique index that you created on the NonMember table can be deleted as
follows:

       DROP INDEX idxNMemSer;

       Index dropped.

You can verify if the index is deleted by viewing the USER_INDEXES data dictionary
view.


       SELECT index_name
© SQL Star International Ltd.                                                     356
FROM USER_INDEXES
       WHERE table_name=‘NONMEMBER‘;

The above statement displays:

       no rows selected.




Index Organized Tables
Each row in a table has a physical location with a unique ROWID assigned to it. As
long as the row exists, its physical ROWID does not change. When you create an
index on a table, the index contains both the column data and the ROWID, and the
index is stored in a memory location separate from the table. As a result, the column
values are repeated, thereby causing redundancy. Secondly, each query that uses
the index increases the I/O operation of following a ROWID back to table data.
Therefore, in Oracle8, concept of Index Organized Tables (IOTs) was introduced.

Index Organized Tables are tables, where the index is created and stored within the
table. Compared to an ordinary table, an IOT has its own way of structuring, storing
and indexing data. A row in an IOT does not have a permanent physical address and
can move across data blocks when new rows are inserted.

An IOT is implicitly indexed on the primary key. The table data is sorted in order of
the B-tree index, which is created on the primary key of the table. The IOTs provide
fast access to table data for queries involving exact match or range search based on
a primary key. It also reduces storage requirements as the indexed column values
are not duplicated in both the table and the index and no additional storage is
needed for ROWIDs.

Index Organized Tables are ideal for the following kinds of applications:


    Online Transaction Processing (OLTP)

    Internet (search engines and portals)

    E-Commerce
© SQL Star International Ltd.                                                    357
 Data Warehousing

    Time-series applications

The syntax to create an Index Organized Table includes an additional
ORGANIZATION INDEX clause in the CREATE TABLE command.




The following command creates an IOT StudentDetails, with studentID as primary
key column:

CREATE TABLE StudentDetails
(studentID CHAR(2), studentName VARCHAR(40),
 courseID CHAR(2), marksTot NUMBER(4),
 CONSTRAINT student_c_pk PRIMARY KEY (studentID))
 ORGANIZATION INDEX;

 Table created.

The ORGANIZATION INDEX clause indicates that the table should be an IOT.

Do queries fail to use index?
Yes, in some cases queries fail to use an index. Let us see some cases here.

Case 1:

If the indexed column is mentioned along with a function, the index usage will be
nullified.
For example:

       SELECT * FROM Member WHERE UPPER(cFirstName)=‘VELADA‘;

This results in Full Table Scan (FTS). This is because, we have indexed on
cFirstName column not on UPPER (cFirstName).

N.B : We can index the function if we choose to do it using Function Based Index.

Case 2:

The indexed column, cPhone has numeric data. But since no calculations are done on
it, it is defined as a character column.

When a query is given with a following syntax,

       SELECT * FROM Member WHERE cPhone=9600102033;

Note that the phone number is not given in single quotes, so while processing,
Oracle will process it as shown below.

       SELECT * FROM Member WHERE TO_NUMBER(cPhone)=9600102033;

Hence, it will not use the index.
© SQL Star International Ltd.                                                       358
How do we check the usage of the Index?

In order to check the usage of the index for a given query, developers can use a
statement as a tool known as EXPLAIN PLAN to determine the execution path of an
SQL statement.

The Execution plan is stored in a TABLE called PLAN_TABLE whose structure is
described below.

       SQL > DESC PLAN_TABLE
The structure of the table will be shown as:

Name                                Null?          Type
---------------------                --------      ---------------
STATEMENT_ID                                        VARCHAR2(30)
PLAN_ID                                             NUMBER
TIMESTAMP                                           DATE
REMARKS                                             VARCHAR2(4000)
OPERATION                                           VARCHAR2(30)
OPTIONS                                             VARCHAR2(255)
OBJECT_NODE                                         VARCHAR2(128)
OBJECT_OWNER                                        VARCHAR2(30)
OBJECT_NAME                                         VARCHAR2(30)
OBJECT_ALIAS                                        VARCHAR2(65)
OBJECT_INSTANCE                                     NUMBER(38)
OBJECT_TYPE                                         VARCHAR2(30)
OPTIMIZER                                           VARCHAR2(255)
SEARCH_COLUMNS                                      NUMBER
ID                                                  NUMBER(38)
PARENT_ID                                           NUMBER(38)
 ....                                               .....
 ....                                               .....



Syntax for using EXPLAIN PLAN:
      EXPLAIN PLAN FOR <statement>;

Case 1.

Consider querying from the Member table with out any index.

      SQL> EXPLAIN PLAN FOR SELECT * FROM Member WHERE
cArea=‘Allenbury‘;

Displays:

       Explained.

In order to get the formatted output of the execution plan, run the following script.

       SQL> @<Oracle_home>RDBMSadminutlxpls


       PLAN_TABLE_OUTPUT

© SQL Star International Ltd.                                                      359
-------------------
       Plan hash value: 3441279308

----------------------------------------
| Id | Operation         | Name | Rows | Bytes | Cost (%CPU)| Time       |
------------------------------------------------------------------
| 0 | SELECT STATEMENT |               | 2 | 24 | 3 (0)| 00:00:01 |
|* 1 | TABLE ACCESS FULL| MEMBER | 2                | 24 | 3 (0) | 00:00:01|
--------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------

PLAN_TABLE_OUTPUT
--------------------------------------------

  1 - filter(―CAREA‖=‘Allenbury‘)

17 rows selected.



The above plan indicates that FULL access is done on the Member table.
We can also see the COST of executing the statement (COST=3), expected number
of rows to be returned and how many bytes of output will be returned.




Case 2.
Let us create an index on the cArea column and re-execute the SQL statement.




       SQL> CREATE INDEX myindex ON Member(cArea);

       Index created.

       SQL> EXPLAIN PLAN
        2 FOR
        3 SELECT cArea FROM Member WHERE cArea=‘Allenbury‘;

© SQL Star International Ltd.                                                  360
Explained.

       SQL> @<Oracle_home>RDBMSadminutlxpls.sql


PLAN_TABLE_OUTPUT
--------------------------------
Plan hash value: 1648515940

---------------------------------------
| Id | Operation | Name | Rows | BytesCos(%CPU)| Time |
--------------------------------------------
| 0 | SELECT STATEMENT |              | 2 | 24 | 1 (0) |00:00:01 |      |* 1 |
INDEX RANGE SCAN|MYINDEX | 2 | 24 | 1 (0) | 00:00:01 |
---------------------------------------------

Predicate Information (identified by operation id):
-----------------------------------------------

PLAN_TABLE_OUTPUT
-------------------------------------

  1 - access(―CAREA‖=‘Allenbury‘)

       17 rows selected.


Here the output very clearly shows that the query uses index access (MYINDEX).
Note that the cost of executing the statement (COST=1) is much less here compared

to the previous case.




Sequences

A sequence is a database object used to automatically generate sequential integers
for primary key columns.

Sequences generate and store numbers, which are not dependent on any particular
table. Hence, sequences can be applied to any table that requires a unique identifier
for each row.

The purposes of generating sequences are:

 The integer values are automatically generated by an internal Oracle server
     routine and therefore, time is saved that would have been otherwise required
     to write a sequence generating application code.
    Sequences that are generated are independent of any table. Therefore,
      multiple users can use the same sequence.
© SQL Star International Ltd.                                                     361
Sequences are most commonly used to populate those primary keys that are not
used for accessing data stored in tables. This is because there are drawbacks
associated with generating sequences to populate primary key columns.

For example, the IDs assigned to members, help to identify them as being unique
from one another. But if these unique IDs are created by sequences, they could
result in some gaps in the sequential values generated, thereby rendering the
primary key values meaningless.

These gaps in sequences result in the following circumstances:

    If inserting sequence-generated values into the primary key column fails, the
      statement gets rolled back and the number is lost.
    If there is a system crash while generating sequential numbers, the number is
      lost.
        As the same sequence can be used for multiple tables, each table will have
         different values for their primary keys. For example, sqSerialNo sequence is
         used for inserting ten rows into the Book table. By doing so, its primary key
         would have the values from 1 to 10. Later, if the same sequence were used to
         insert ten rows into the Member table, its primary key would have values
         beginning from 11 to 21. This shows that any subsequent use of the same
         sequence by the Book or the Member table would generate different value

Using Sequences

You can create sequences based on some rules and clauses. These help the
sequences to generate unique integers in a special order. You can also ensure that
their performance is optimized.



Creating Sequences

The syntax to create a sequence is as follows:


         CREATE SEQUENCE sequence
               [START WITH n]
               [INCREMENT BY n]
               [(MAXVALUE n | NOMAXVALUE)]
               [(MINVALUE n | NOMINVALUE)]
               [(CYCLE | NOCYCLE)]
               [(CACHE n | NOCACHE)];

Where,

sequence is the name of the sequence that will generate the numbers.

© SQL Star International Ltd.                                                     362
START WITH n is the first value that the sequence generates.

INCREMENT BY n is the value with which each integer of the sequence will be
incremented. If you do not specify a value the default incrementing value is 1.

MAXVALUE n is the value that is the highest integer to be generated by the
sequence. If you do not want a maximum limit you can use the NOMAXVALUE
option.

NOMAXVALUE is 10^27 in ascending and –1 for descending sequences. The latter
figure is the default value.

MINVALUE n is the value that is the lowest integer to be generated by the sequence.
You can use the NOMINVALUE option if you do not want to specify any minimum
value. This value is ‗1‘ in case of an ascending value and 10^27 in case of
descending value.

CYCLE | NOCYCLE allows you to specify if you want the sequence to continue
generating numbers after reaching the maximum or minimum values. The numbers
generated are recycled. For instance if the minimum value is ‗1‘ and the maximum is
‗10‘ and you specify CYCLE then the 11th number will be ‗1‘ and so on.

Specify NOCYCLE if you do not want the numbers to continue being generated.

CACHE n | NOCACHE respectively is specified if you want or do not want some values
to be pre-allocated and stored in memory by the server. By default 20 values are
cached.

The syntax clearly shows that there are many rules available that allow developers to
define how the sequence numbers are to be generated.

For instance, the library database developer decides to create a sequence that
generates serial numbers, which could be made use of by any user for any table. The
following code illustrates the creation of this sequence:
       CREATE SEQUENCE sqSerialNo
       START WITH 1
       INCREMENT BY 1
       MAXVALUE 1000;

On the successful execution of the above code, you get the following message:

       Sequence created.


Viewing Sequence Information

Like other database objects, information about sequences is also stored in the
system in a data dictionary.


© SQL Star International Ltd.                                                    363
You can view and confirm the information on the structure of a sequence by using
the USER_SEQUENCES data dictionary.

The structure of USER_SEQUENCES can be verified by issuing the DESCRIBE
command.

       DESCRIBE USER_SEQUENCES

Displays:
       Name                                 Null?              Type
       ------------          ---------      ---------
       SEQUENCE_NAME             NOT NULL           VARCHAR2(30)
       MIN_VALUE                                               NUMBER
       MAX_VALUE                                               NUMBER
       INCREMENT_BY              NOT NULL           NUMBER
       CYCLE_FLAG                                              VARCHAR2(1)
       ORDER_FLAG                                              VARCHAR2(1)



       CACHE_SIZE                        NOT NULL        NUMBER
       LAST_NUMBER                          NOT NULL     NUMBER


You can retrieve the minimum and the maximum values specified for the sequences,
along with their incremental values by querying USER_SEQUENCES as shown below.


       SELECT SEQUENCE_NAME,MIN_VALUE,
       MAX_VALUE,INCREMENT_BY,LAST_NUMBER
       FROM USER_SEQUENCES;

Displays the following result:

       SEQUENCE_NAME MIN_VALUE MAX_VALUE INCREMENT_BY LAST_NUMBER
       ------------- --------- --------- ------------ -----------
       SQSERIALNO              1      1000      1         27




© SQL Star International Ltd.                                                  364
Using NEXTVAL and CURRVAL

After you have created a sequence, you need to be able to view the values in it. To
query data from tables with sequences, use the CURRVAL and the NEXTVAL
keywords. These keywords represent virtual columns or pseudocolumns.

The NEXTVAL pseudocolumn retrieves the next available sequence number from a
specified sequence. The CURRVAL pseudocolumn returns the current sequence value
that gets generated by NEXTVAL. But to extract the values that NEXTVAL and
CURRVAL return, you need to reference them in a SELECT statement issued against
the DUAL table.

NEXTVAL and CURRVAL are referenced in the SELECT statement by prefixing them
with the sequence name.

When you pass the command sequence.NEXTVAL, a new number is generated and
the current number is stored in CURRVAL. sequence.CURRVAL displays the number
that was last returned to the user.




When you access NEXTVAL, the value in CURRVAL is the accessed value of NEXTVAL
and the previous value in CURRVAL is lost.

The values are generated according to some rules that are set when developing the
sequence.

Given below is a list of restrictions on sequences:

    You can only display data from the pseudocolumns and not insert data into
      them.
    Avoid using the pseudocolumns in an INSERT and UPDATE triggers. This
      action causes the session in which the trigger has been fired to end
      abnormally.
    You cannot use them when selecting from a view.
    SELECT statements with the DISTINCT keyword, GROUP BY, HAVING or
      ORDER BY clauses cannot include these columns.
    They cannot be referenced in a DEFAULT expression in a CREATE TABLE or
      ALTER TABLE statement.

You can, however, reference these values in:

      The   SELECT list of a SELECT statement, which is not part of a subquery
      The   SELECT list in a subquery used in an INSERT statement
      The   VALUES clause in an INSERT statement
      The   SET clause of an UPDATE statement

The New Jersey Central Library maintains a table to store details of non-members,
that is, those, whose membership has been terminated either due to failure in
returning borrowed books after repeated reminders, or those who have terminated

© SQL Star International Ltd.                                                      365
the membership on their own will. The sequence sqSerialNo can therefore be used
for the purpose of inserting rows into the NonMember table as shown below.


       INSERT INTO NonMember (nSerialNo, cMemberID,
       cFirstName, cLastName, cPhone,dMembershipDt)
       VALUES (sqSerialNo.NEXTVAL,‗CAC0989‘,
       ‗Angela‘,‗Clarke‘,‗9082233‘,‗12-SEP-89‘);


       1 row created.

To view the current value issue the following statement:


       SELECT sqSerialNo.CURRVAL
                FROM DUAL;
                CURRVAL
                -----------
            1

Some points that you need to remember while using sequences:

    You can access the sequence values faster by caching the values. When a
      reference is made to the sequence, some values are put into memory.
      Sequence      values are retrieved from the cache each time it is requested.
      Once the values in cache are over, the next request for a sequence value
      causes another set of values to be cached.
    Gaps in a sequence are not advisable. Sequences are generated in a
      sequential manner, but incase a ROLLBACK is done, the value is lost. In the
      event of a system crash the values in cache are lost. Sequences can be used
      for more than one table and thus in such a case gaps in the sequences will be
      seen in each table that it is used.
    You can view the next value in a sequence without incrementing it, even if
      you specified NOCAHCE while creating the sequence.



Manipulating Sequences
You have seen that you can alter a table in case you want to change the definition of
some column. Similarly, you can also change the definition of a sequence.

In case you want to increase the maximum value of the sequence, you can change
its definition to include a higher value.
The syntax do so is:
       ALTER SEQUENCE sequence
                [INCREMENT BY n]

© SQL Star International Ltd.                                                    366
[(MAXVALUE n | NOMAXVALUE)]
              [(MINVALUE n | NOMINVALUE)]
              [(CYCLE | NOCYCLE)]
              [(CACHE n | NOCACHE)];

The syntax is the same as that for creating the sequence, but the name used is the
name of the sequence already created and needing modification. You can change any
parameter of a sequence except the START WITH parameter.

Some points to remember when modifying a sequence are:
    You need to be the owner of the sequence and have the right to alter it.
    You need to be careful when changing a sequence as the future values
   generated are the ones that are affected by the change.
   
   
    If you want to change the starting value of the sequence then you need to
   drop and recreate the sequence as this value cannot be changed using the ALTER
   SEQUENCE statement.

    Care must be taken to ensure not to reset the maximum value to a value
   lower than the current sequence number.

Suppose you have reached the maximum value specified for the sequence
sqSerialNo, then the sequence stops generating any additional numbers and
displays an error stating that the sequence has surpassed the MAXVALUE. If
however, you wish to continue using the sequence, then you need to modify it. But
while modifying, if you specify a maximum value lower than the current sequence
number generated, you would encounter an error. To view the error, issue the
following ALTER SEQUENCE statement:


       ALTER SEQUENCE sqSerialNo
       INCREMENT BY 1
       MAXVALUE 999;

Displays:


       ALTER SEQUENCE sqSerialNo
       *
       Error at line 1:
       ORA-04009: MAXVALUE cannot be made to be less than the current value.


Dropping a sequence


© SQL Star International Ltd.                                                    367
You can delete a sequence from the data dictionary by using the DROP SEQUENCE
statement.

The syntax is:

         DROP SEQUENCE sequence;

If the purpose for which the sequence was created has been accomplished, you can
remove it.

         DROP SEQUENCE sqSerialNo;




Synonyms

You now know how to create various database objects such as tables, views, indexes
and sequences. However, when it comes to accessing these objects owned by some
other users, then you need to prefix the object names with the names of their
owners. This proves to be quite cumbersome especially when the names are lengthy.
Hence, an object known as synonyms, which simplifies the accessing of objects
owned by other users can be created.

Synonyms enable the users to provide alternative names to objects and thereby do
away with the need to prefix object names with their owner‘s name. The syntax to
give another name to an object is as follows:


         CREATE [PUBLIC] SYNONYM <synonym_name>
         FOR <object_name>;

Where,

PUBLIC specifies that the synonym created can be accessed by all users.

synonym_name is the alternative name given to the desired object.



© SQL Star International Ltd.                                                 368
object_name specifies the object (table, view, sequences or indexes) for which a
synonym is to be created.


Using Synonyms

Synonyms are of two kinds, PUBLIC and PRIVATE. Owners of database objects create
private synonyms, especially when their objects have lengthy names, which make
them difficult to remember. For instance, ‗Lisa‘ may decide to create a synonym for
the vwRandolphBook view created by her. To do so, she would create the following
private synonym:


       CREATE SYNONYM RandolphBk
       FOR vwRandolphBook;

The following message is displayed on successful creation of the sequence:

       Synonym created.




Only the user DBA creates a public synonym, so that it could be accessible to all
users. For example, the user DBA decides to create a public synonym for Brad‘s
NonMember table as follows:
       CREATE PUBLIC SYNONYM NonMember
       FOR Brad.NonMember;

After creating a synonym, the user or the user DBA could drop it using the DROP
SYNONYM statement. However, only the user DBA can drop a public synonym as
follows:

       DROP SYNONYM BridgetonBk;

       Synonym dropped.

Issuing this statement removes the synonym from the database.




© SQL Star International Ltd.                                                       369
Summary
In this chapter, you have learnt that:

      An index is a database object with which you can increase the speed of data
      retrieval. Indexes are created automatically when Primary key or Unique key
       constraints are added to the table. Indexes can also be created manually.

     The different types of Indexes are:
       B-tree index, Bit-map index, Unique index, Non Unique Index, Compressed
   Index, Function-based index.
       EXPLAIN PLAN statement helps us to know the execution details of a
   particular statement.

    Sequence is a database object used to generate automatic numbers.
   Pseudocolumn NEXTVAL and CURRVAL are used to generate a sequence. A newly
   created sequence should be first invoked with NEXTVAL. To check the current
   generated value, use the CURRVAL pseudocolumn.

    Once a sequence generates a number, it cannot be rolled back. Also, we
   cannot use the START WITH clause in the ALTER statement of a sequence.

      Synonyms are database objects used to give alternative names to the exisit
   objects.




© SQL Star International Ltd.                                                  370
Lab Exercise
Create a sequence that can be used with primary key column of the new_dept
table. The sequence should start with 200 and have a maximum value of 1000.
Name the sequence as NEW_DEPT_ID_SEQ and the sequence should increment by
20.

Display the information about your sequence- the sequence name, maximum value,
increment size and the last number.




1.      Insert three rows into the new_dept table. Use the sequence you created for
        the deptID column. Add three departments namely, ‗Marketing‘,
        ‗Administration‘ and ‗Education‘. Confirm whether the rows have been inserted




2.      Create an index on the foreign key column of the new_emp table.


3.      Display the indexes and the uniqueness that exist in data dictionary table for
        the new_emp table.




      Create a synonym for the new_dept table.




© SQL Star International Ltd.                                                            371
Chapter 16




                                Data Dictionary Views
                                         Structure of Dictionary Views
                                       Purpose of the Dictionary Views
                                   Querying Data Dictionary Views




© SQL Star International Ltd.                                     372
Objectives


At the end of this chapter, you will be able to:

   Understand available Data dictionaries in Oracle

   Query Data dictionary Views

Understand Dynamic Performance Views v$




© SQL Star International Ltd.                              373
Data Dictionary
A Data Dictionary is nothing but a set of read only tables that provides information
about its associated database. It provides information for all types of users right
from end users to administrators. It indirectly gets updated under the influence of a
DML or DDL Operation. There are hundreds of data dictionary tables and views.
These views are built on underlying base tables such as SYS.TAB$.
The static data dictionary views contain information about database objects such as tables,
indexes and procedures. They are called “static” because the contents of the views change only
when DDL operations are executed. For example, a row is added to the USER_TABLES view
when any user successfully executes a CREATE TABLE statement. (There are also dynamic
views, which we will discuss later in this chapter.)

There are three types of static views:

1. USER_

2. ALL_

3. DBA_
Where,
USER_ level views contain information about the current user’s objects.

ALL_ level views contain information about the users objects and objects in other schemas that
the user has some privilege on.

DBA_ level views are accessed by administrators.




Characteristics of Data Dictionaries

    Following are some of the characteristics of Data Dictionaries:

       Cannot be shared across Database(DB)
© SQL Star International Ltd.                                                            374
Describe the database and objects contained in it

    Can be accessible with simple SELECT

    Maintained by the Oracle server

    Read only

    Contains Base tables and Data dictionary views

A Base table is an internal table, which is automatically created during Database creation. Only
Oracle server has the privilege to write it. An example of the base table is the IND$ table, which
gets populated while creating indexes for application development.

Data Dictionary Contents
The tables and views provided by the data dictionary contain information about:

           Entire Database structure

           Tables and indexes

           Integrity Constraints

           User Information

           Privileges granted on database objects




Usage Of Data Dictionaries

Data dictionaries are primarily used for Object resolution during any SQL OR PL/SQL operation.

For example,

        SELECT * FROM Member WHERE nAge>6;

requires a verification, whether

    (1) The table Member exists

    (2) The user has the privilege to access this table

    (3) The column nAge has been defined for this table etc.
© SQL Star International Ltd.                                                                375
List of Data Dictionary Views
The following SQL command

       SELECT * FROM DICT[IONARY];

lists all tables and views of the data dictionary that are accessible to the user. The
selected information includes the name and a short description of each table and
view. Before issuing this query, check the column definitions of DICT[IONARY] using

       SQL> DESC DICT[IONARY]

and set the appropriate values for column using the format command.

USER_    DATA DICTIONARY VIEWS

This holds the information of the objects created by the user.

USER_TABLES: All tables with their name, number of columns, information,
statistical information etc. (TABS)

USER_COL_COMMENTS: Comments on columns

USER_CONSTRAINTS: Constraint definitions for tables

USER_INDEXES: All information about indexes created for tables

USER_OBJECTS: All database objects owned by the user

USER_TAB_COLUMNS : All Columns of the tables and views owned by the user



USER_TAB_COMMENTS: Comments on tables and views.

USER_TRIGGERS: Triggers defined by the user
USER_VIEWS:                  views defined by the user


ALL_ DATA DICTIONARY VIEWS

Rows in the ALL views include rows of the USER views and all information about
objects that are accessible to the current user. The structure of these views is
analogous to the structure of the USER views.

ALL_CATALOG: owner, name and types of all accessible tables, views and synonyms

ALL_TABLES: owner and name of all accessible tables

ALL_OBJECTS: owner, type and name of accessible database objects



DBA_ DATA DICTIONARY VIEWS


© SQL Star International Ltd.                                                     376
The DBA views encompass information about all database objects, regardless of the
owner. Only users with DBA privileges can access these views.

DBA_TABLES: tables of all users in the database

DBA_CATALOG            : tables, views, and synonyms defined in the database
DBA_OBJECTS                  : object of all users

DBA_DATA FILES: information about data rules

DBA_USERS: information about all users known in the database

Following is an illustration to use a Data Dictionary View:



       SELECT OBJECT_NAME, OBJECT_TYPE, CREATED, STATUS
       FROM USER_OBJECTS;


Object_type can be any of the database objects like table, Index, views, synonym,
sequence or any objects created in PL/SQL programming like procedures, functions
or triggers etc.
Created indicates the date of creating the object. Note that a conversion function
to_char can be used to get the time.


Status indicates whether it is a valid database object or not. Invalid status requires
recompilation in certain PL/SQL objects.
Note: A view would become invalid, if the underlying base table undergoes any
structural change.
Below is the output of the above query.




 -------------------
 45 rows selected.
© SQL Star International Ltd.                                                     377
Commenting a Table Or Column

A table or a column in a table can be provided with comments up to 2000 bytes in
10g. These are registered primarily in 4 data dictionaries for future reference
namely,


          ALL_COL_COMMENTS


          USER_COL_COMMENTS


          ALL_TAB_COMMENTS


          USER_TAB_COMMENTS


In addition to these, there is a dictionary called   DBA_TAB_COMMENTS, WHICH is
used only by the DBA.
To add a comment on the table issue the following command.


       COMMENT ON TABLE Member IS ‗ To maintain library member information‘;
This comment will be recorded in USER_TAB_COMMENTS

Dynamic Performance Views V$

These views are virtual tables in which the Oracle server records all the activities
happening in a database dynamically. This will reside only in memory and will not
occupy any space in any of the schema.




V$ views are handled only by administrators to get information such as:


        Is the database open?


        Is there any session hanging?

© SQL Star International Ltd.                                                          378
 Is the database performance optimal?


        Trouble shooting related information.


Examples of V$VIEWS are:


V$SESSION: To know the details of a list of users connected to the database.


V$SGA: Information regarding Memory


V$DATAFILE: List of Datafiles that belong to the database.


There are thousands of dynamic performance views available in Oracle.


Summary

In this chapter, you have learnt that:

       A data dictionary is nothing but a set of read only tables that provides
   information about its associated database. It indirectly gets updated under the
   influence of a    DML or DDL Operation.

       Views created on these Data dictionary tables are accessed by the users for
   retrieving metadata information.

      A Data dictionary view can be a static view or a dynamic view. Static views
   are USER_,(having specific user related information) ALL_,( owned as well as
   accessible objects information) DBA_(all information accessed by DBA) and
   dynamic views are V$.(information related to your database)




© SQL Star International Ltd.                                                  379
Lab Exercise

   1. Write a query to check the available tables in your schema.

   2. Write a query to see the different objects created in your schema.

   3. Display the object names and types from the USER_OBJECTS data dictionary
      view for the New_Emp and New_Dept tables.

   4. Add a comment on the Employees table and view it.

   5. Can you access DBA related tables in your schema. If no, what errors do you

      get?




© SQL Star International Ltd.                                                 380
Chapter 17




                                Security Implementation
                                      Introduction to user access control
                                          Security Model of the Database
                                                          Creating users
                                              Granting system privileges
                                            Creating and Managing roles
                                               Granting object privileges
                                Query Data Dictionary View for privileges
                                              Revoking object privileges




© SQL Star International Ltd.                                        381
Objectives
At the end of this chapter, you will be able to:

Identify the security requirements of a database

Identify the database system privileges

Create Database Users

Change User password for security

Create roles to grant privileges to users

Grant and revoke object privileges




© SQL Star International Ltd.                          382
Introduction to User Access Control
Organizations started using databases due to the huge amounts of data and the
functional requirements of accessing the data frequently. But another aspect of
organizations is the number of people working there who would access the database
regularly. Just as it is important for a bank to keep its money safe with just one or
two people permitted to access it, similarly each organization‘s data is critical to
them and needs to be handled by the right people. With hundreds of people in the
organization accessing the database, security of the database becomes an important
issue for the administrators to concentrate on.


Methods of Controlling User Access
There are various methods by which you can control the user access on the
database. They are:

      Setting system privileges

      Creating roles for users to restrict database access

      Setting object privileges

      Changing passwords assigned to users

      Granting and revoking object privileges

      Creating synonyms for database transparency


Security Model of the Database
Security for the Oracle database is divided into two parts. The first part is the
password security provided by the operating system or the Oracle server. The other
security model is controlling the access users have to database objects.

A database administrator (DBA) or the security administrator for the organization is
responsible for the security of the databases. For organizations that are large and
work with highly critical data, it is better to have one person dedicated to implement
security for the database.


Privileges
The right to execute particular SQL statements is referred to as privilege(s). The
DBA, who is the high-level user, has the power to grant access to the database and
its objects, to the users.

To gain access to the database, users require system privileges and to manipulate
the content of the objects within the database, they require object privileges.




© SQL Star International Ltd.                                                     383
System Privileges
System privileges are certain rights and restrictions that are implemented on the
database, so that you can control the access, people have to the database.
There are over 100 system privileges available. System privileges are provided
typically by the DBA. A few of the typical DBA privileges are listed below.

DBA System Privileges




Once a DBA creates a user, the DBA can assign specific system privileges to the
user. These are known as user system privileges. A few of the typical user privileges
are listed below.

User System Privileges




© SQL Star International Ltd.                                                    384
Creating Users
The first task that needs to be done is to allow the users to access the database.
Only then, will you be able to implement control on their access. To allow people to
use the database, you need to create ‗users‘, as are understood by the database. All
personnel who have access to use the database will have a different name and
password assigned to them.
You can create users by using the CREATE USER command. The syntax is:

       CREATE USER <user>
       IDENTIFIED BY <{password | externally}>;
Where,
User is the name you want to give the user

Externally is specified when you want the system and database log on to be the
same. In this case you need not give a password and when you log on to your
machine, you will get connected to the database server without specifying the
username and password.
Password allows the user to access the database by giving the password specified.
An example of creating a user with a password is:

       CREATE USER LISA
       IDENTIFIED BY MYDATA;
       User created.

A password is a secret character string, known only to the user. Passwords are set
after a user account is created. At first, users are given a default password. They can
change it with the following statement.

       ALTER USER Lisa IDENTIFIED BY bugsbunny
       User altered.

You could also use the PASSWORD command to change the password.
The PASSWORD command, when typed, prompts the user for the old password, the
new password and confirmation of the new password.
The password security does not allow too many attempts in case you have forgotten
your password and the account may be locked. It is a good practice to change your
password regularly but not too often. When you change your passwords ensure you
maintain a history of your passwords so that you do not reuse an old one. There is
also a feature that allows you to set the maximum and minimum size of a password.


© SQL Star International Ltd.                                                      385
The expiry of passwords depends on the profile assigned to your account. Profiles
determine the following:

      Time period for which a password holds good

      Grace period given to change the password

      Number of attempts to log on to your account after which the account is
        locked

      Number of days the account is locked

      Number of days and other passwords to be used before reusing a password

Granting System Privileges to Users
System privileges are given with the GRANT command. The syntax is as follows:
        GRANT privilege [, privilege…]
        TO user [, user | role, PUBLIC…];
Where,
privilege is the system privilege to be granted
user | role is the name of the user or role
PUBLIC specifies that every user is granted the privilege
User ‗Lisa‘ (created in the previous section) could be granted the user system
privileges as follows:

        GRANT CREATE SESSION, CREATE TABLE, CREATE SEQUENCE, CREATE VIEW
        TO LISA;
        Grant succeeded.




A System privilege that is granted with the WITH ADMIN OPTION clause can be
passed on to other users by the grantee. SYSTEM privileges granted with the WITH
ADMIN OPTION clause are NOT revoked when the grantor‘s privilege is revoked.




© SQL Star International Ltd.                                                 386
DBA                            User1                         User2




In the event of DBA revoking the privilege from user1,        user2 still enjoys the
privilege.




Roles
So far you have created a user account for ‗Lisa‘ and given her some system
permissions. You may create many such user accounts for all the personnel in the
organization and give them privileges. But when the size of the database and the
organization increases, it will be difficult to manage all the user accounts and the
privileges. This makes management of database security more critical. Hence, to
make this easier you can create roles.


Creating Roles for Database Access
A role is the functional part, one plays. For example, an actor or actress performs a
role in movies or a person of an organization plays a role like those of a finance
manager or marketing executive among many others. When used in relation to a
database a role means the same. Many privileges can be grouped under a particular
role. This enables easy management of privileges. Roles are also used as virtual
privileges.

The activities you need to perform to start using roles are:
    1. Identifying the similar privileges and grouping them together.
    2. Grouping together the various users of the database according to their usage
       requirements.
    3. Create the role.
    4. Grant the identified set of privileges to the role.
    5. Grant the role to the identified group of users.
The syntax for creating a role is:
       CREATE ROLE <role_name>;
Where,
role_name is the name assigned to the role to be created.
Just as a user name is created with password protection, a role can also be created
with password protection. For example,
       CREATE ROLE MktAnalysis IDENTIFIED BY analyzemarket;
© SQL Star International Ltd.                                                    387
Role created.
The DBA can now assign privileges to the role MktAnalysis using the GRANT
statement as follows:
      GRANT CREATE VIEW TO MktAnalysis WITH ADMIN OPTION;
      Grant succeeded.

The above role MktAnalysis can now be assigned by the DBA to users using the
GRANT statement as follows:
       GRANT MktAnalysis TO Lisa, Maria;
       Grant succeeded.
To assign roles to users, you need to classify the users based on the activities they
perform and the privileges they require to perform these activities. Hence based on
these, the roles will be granted privileges.
The three default roles are:

      CONNECT: Enables the users to connect to the database and access data.
        This role is not assigned the privilege to create tables in the database. The
        privileges of this role can be further controlled by giving specific rights on
        tables with different owners and specifying whether the role can perform a
        query, an insert, update or delete on the tables.

      RESOURCE: A role assigned to those users who use the database more
        regularly. A user with this role has the right to create database objects.

      DBA: A role with the highest privileges. The database administrator is
        responsible for giving and revoking the system privileges from other users
        and roles. There are two kinds of privileges, DBA and system. DBA privileges
        are available with the DBA role and system privileges are meant for a DBA
        user. A DBA also has the rights to export and import the database. For this
        they are given the roles of EXP_FULL_DATABASE and IMP_FULL_DATABASE.

Managing Roles
You can alter a role using the ALTER ROLE IDENTIFIED BY statement. You can also
delete a role using the DROP ROLE statement. When you drop a role, the user
belonging to that role will not have any of the privileges that were attached to the
role. To be able to perform these activities you need to have the CREATE ANY ROLE,
ALTER ANY ROLE and DROP ANY ROLE privileges. Privileges can be revoked from a
role as is done for users using the REVOKE statement.
By default, roles are enabled and would have to be disabled explicitly if required.
When a role is to be assigned to a user, the required role should be enabled. The
ALTER USER DEFAULT ROLE statement needs to be implemented if you want to
change the status of the role for a user in any of the following ways:
        ALTER USER lisa DEFAULT ROLE ALL;
        ALTER USER lisa DEFAULT ROLE ALL EXCEPT dba;
        ALTER USER lisa DEFAULT ROLE mktanalysis, statdata;
        ALTER USER lisa DEFAULT ROLE NONE;




© SQL Star International Ltd.                                                     388
Object Privileges
Once you create an object in a database, there might be situations where the object
would have to be changed. Not all users are allowed to manipulate database objects.
You (the owner) or the administrator have control over the objects and can
manipulate it. If a user has the GRANT ANY PRIVILEGE system privilege then he or
she can also control the object.
To be able to make changes to database objects you need to have privileges on an
object. These are called object privileges. Object privileges enable you to perform
specific actions on specific objects. Different objects have different privileges granted
for it.
Following is a list of object privileges and the objects they can be applied to:

      ALTER: tables and sequences

      DELETE: tables and views

      EXECUTE: procedures

      INDEX: tables

      INSERT: tables and views

      REFERENCES: tables

      SELECT: tables, views and sequences

      UPDATE: tables and views

Granting Object Privileges
You grant the object privileges mentioned above with the GRANT command. The
syntax is as follows:
       GRANT <object_privilege| ALL> [(columns)]
       ON <object>
       TO {user | role | PUBLIC}
       [WITH GRANT OPTION];

Where,
<object_privilege> is one of the object privileges to be granted.
ALL is specified when you want to grant all the privileges.
columns of a table or view to which privileges are to be granted.
ON object, the object on which the privilege is granted.
TO {user | role | PUBLIC} specifies that the privilege can be granted to either a user
or a role or to all the users .PUBLIC Keyword is used for all users.
WITH GRANT OPTION allows the user with the privilege to grant the same to others.
© SQL Star International Ltd.                                                        389
The syntax of granting Lisa the right to insert data into the Member table is given
below.
       GRANT INSERT
       ON Member
       TO Lisa;
If you want to restrict the columns that she can update you may give the following
command:
       GRANT UPDATE (vAddress, cPhone)
       ON Member
       TO Lisa;
Some points to remember about object privileges are:

      Object privileges vary for different objects.

      Owners of objects have all the privileges associated with the objects.

      Users get the privileges for all objects on their schema.

      Grantees can either grant the privileges to other users or not grant them to
        others.

      To grant a privilege, you must be the owner of schema or have the WITH
        GRANT OPTION.

When you are granted privilege on an object in another schema, you need to access
the object by prefixing it with the name of the schema. For example, ‗Lisa‘ has been
given privilege to enter data into the Member table. The Member table is in the
schema owned by ‗Jack.‘ So ‗Lisa‘ will have to execute the following statement:


        INSERT INTO Jack.Member (cFirstName, cLastName)
        VALUES (‗Sandy‘, ‗Prill‘);


Viewing the Privileges
You can confirm the privileges granted to users by querying the data dictionaries.
Following is the list of data dictionaries that can be queried:

      ROLE_SYS_PRIVS to see system privileges granted to roles

      ROLE_TAB_PRIVS to see the table related privileges granted to roles

      USER_ROLE_PRIVS to see roles accessible by users

      USER_TAB_PRIVS_RECD to see object privileges granted on the user objects

      USER_TAB_PRIVS_MADE to see object privileges granted to the user

      USER_COL_PRIVS_RECD to see the columns on which privileges have been
        granted

     USER_COL_PRIVS_MADE to see the object privileges granted to users on
       specific columns
In case you do not know what privileges you have, you can query these data
dictionary views to check the privileges. If you perform an activity for which you do

© SQL Star International Ltd.                                                    390
not have privileges, the transaction will not be performed and an error message will
be displayed.

Revoking Privileges
You can also revoke privileges from users and roles, by using the REVOKE
statement. The syntax for revoking is as follows:
       REVOKE <object_privilege, object_privilege, …| ALL> [(columns)]
ON <object>
FROM {user, user, . . . | role | PUBLIC}
[CASCADE CONSTRAINTS]
While revoking, you can revoke more than one privilege from more than one user or
role or the public at a time.
CASCADE CONSTRAINTS is specified if you want to remove any integrity constraints
that come with granting the REFERENCES privilege.
If there has been a chain of grants enabled by the WITH GRANT OPTION from user
to user, then when the owner revokes the privilege from a user who in turn granted
the privilege,
the revoking has a cascading effect on all the privileges granted. Look at the diagram
shown below.


  User 1                        User 2                 User 3




When User1 revokes the SELECT privilege from User2, then the privilege granted to
User3 by User2 is also revoked.




© SQL Star International Ltd.                                                     391
Summary

In this chapter, you have learnt that:

    Restrictive access to the database is implemented by PRIVILEGES. Privileges
   can be divided into SYSTEM privileges and OBJECT privileges.
    SYSTEM privileges are given by the DBA to create database objects. OBJECT
   privileges are given by the users to another user to manipulate database objects.
    PRIVILEGES can be given individually or through ROLES. Role is a schema
   object containing collection of privileges that can be given to the users.
    PRIVILEGES are given to the user by GRANT command and taken back by
   REVOKE command.




© SQL Star International Ltd.                                                   392
Lab Exercise
[Note: For this Lab exercise, you need to team up with other students in order to
implement controlling access to database objects.]
1.     Grant query access on your Employees table to another user. (Assume you
       are user1) In turn have the user (Assume the user to be as user2) grant
       query access on his/her Employees table to you (user1).
2.     Have user1 and user2 insert the following data into their respective
       Employees table:
       user1 : Should add 500 as employee ID, Nancy and Win as the first name
       and last name respectively, nwin@somemail.com as the email ID, 15-Mar-
       2002 as the hire date and ST_CLERK as the job ID.
       user2 : Should add 501 as employee ID, Brown and Rhodes as the first name
       and last name respectively, Brown@mailme.com as the email ID, 15-Mar-
       2002 as the hire date and ST_CLERK as the job ID.
       Will user1 be able to view the new row inserted by user2 on querying
       user2.Employees table? Similarly, will user2 be able to view the new row
       inserted by user1 on querying user1.Employees table? Why? How can they
       view the new rows inserted by one another?
3.     Have user1 create a synonym user2 for user2.Employees table and have
       user2 create a synonym user1 for user1.Employees table.
4.     As a DBA, how would you grant CREATE TABLE, CREATE SEQUENCE and
       CREATE VIEW privileges to user1 and user2. Since, the same set of system
       privileges are to be granted to both the users, is there any way to make your
       job easier? What is the way?
5.     Have the users revoke the SELECT privilege on their respective Employees
       table.




© SQL Star International Ltd.                                                   393
Chapter 18




                          Manipulating Large Data Sets

                                Overview of Multi-table INSERT Statements
                                                        Creating Directories
                                     Creating and querying External Tables
                                       Unloading Data Using External Table
                                    Performing DML with Merge Statement
                                             Using FlashBack Enhancement




© SQL Star International Ltd.                                           394
Objectives

At the end of this chapter, you will be able to:

Perform Multi-table Inserts

Create Directories

Creating and querying External tables

Perform DML with Merge Statements

Tracking changes in DML using VERSION clause




© SQL Star International Ltd.                         395
Introduction

Multi-table INSERT, a feature introduced in Oracle9i, allows you to insert rows into
multiple tables as a part of a single DML statement. Multi-table INSERT statements
were especially designed with regard to data warehousing system. To facilitate
business analysis efficiently, data warehouses must be updated regularly. Multi-table
INSERT statements can be used in data warehousing systems to transfer data from
one or more operational sources to a set of target tables. Prior to Oracle9i, this was
done with independent INSERT…SELECT statements. However, this approach was not
only cumbersome, but also created a heavy load on the Oracle server.

Multi-table INSERTs perform better than:

      Multiple INSERT……SELECT statements
      A procedure to do multiple inserts using IF…THEN syntax

There are four types of Multi-table INSERT statements:

      Unconditional INSERT
      Conditional INSERT ALL
      Conditional INSERT FIRST
      Pivoting INSERT



Multi-table INSERT Statement has the following syntax:


        INSERT [ALL] [conditional_insert_clause]
        [insert_into_clause values clause] (subquery)


The syntax for conditional_insert_clause is:


        [ALL] [FIRST]
        [WHEN condition THEN] [insert_into_clause values clause]
        ELSE [insert_into_clause values clause]




Unconditional INSERT

In an unconditional Multi-table insert statement, there is no restriction on the
insertion of rows into different tables. There may be restriction on the rows that are
retrieved in the subquery. You must specify ALL followed by multiple
insert_into_clause to perform an unconditional Multi-table insert. The Oracle server
executes each insert_into_clause once for each row returned by the subquery.




© SQL Star International Ltd.                                                     396
For example, to insert details of members who were issued books before 1 st January
2001 and details of books issued before 1st January 2001, use an unconditional
Multi-table INSERT statement. First create two tables, namely:

    TransMemberHistory, that holds the transaction details of members who
       were issued books before 1st January‘ 2001. The TransMemberHistory table
       contains columns to store transaction ID, member ID, book ID, issue date
       and fine amount.
   TransBookHistory, that holds the details of books issued before 1 st January‘
       2001. It contains columns to store transaction ID, book ID, issue date, actual
       return date and fine amount.

To perform Multi-table insert into TransMemberHistory and TransBookHistory
tables, issue the following query:


       INSERT ALL
       INTO TransMemberHistory
       VALUES (cTranID, cMemberID, cBookID,dIssueDt, nFine)
       INTO TransBookHistory
       VALUES (cTranID, cBookID, dIssueDt,
           dActualReturnDt, nFine)
       SELECT cTranID, cMemberID, cBookID,
           dIssueDt, dActualReturnDt, nFine
       FROM Transaction
       WHERE dIssueDt<‘01-JAN-2001';


       50 rows created.


In the query, first the transaction details before ‗1st Jan, 2001‘ are retrieved from
the Transaction table. Then, using INSERT ALL statement, the respective values are
inserted into TransMemberHistory and TransBookHistory tables. No condition is
specified in the INSERT ALL statement, hence known as unconditional Multi-table
insert statement.


Conditional INSERT ALL
In conditional INSERT ALL statement, the values to be inserted are filtered based on
some condition. Depending on your requirement, you can give a separate condition
for inserting values into each table or single condition that applies to all tables.
In the TransBookHistory and TransMemberHistory tables, if you wish to insert
only the data of those members who are due to pay a fine, you can use the Multi-
table conditional INSERT ALL statement in the following manner:


       INSERT ALL
© SQL Star International Ltd.                                                    397
WHEN nFIne IS NOT NULL THEN
       INTO TransMemberHistory
       VALUES (cTranID, cMemberID, cBookID,
             dIssueDt, nFine)
       INTO TransBookHistory
       VALUES (cTranID, cBookID, dIssueDt,
             dActualReturnDt, nFine)
       SELECT cTranID, cMemberID, cBookID,
       dIssueDt, dActualReturnDt, nFine
       FROM Transaction
       WHERE dIssueDt<‘01-JAN-2001';


       32 rows created.


In the query, first the details of transaction that occurred before ‗1 st Jan, 2001‘ are
retrieved by the subquery. Only the details of transactions where a fine amount has
to be collected are inserted into the tables TransBookHistory and
TransMemberHistory. The condition for selective insert is specified by the
WHEN…THEN clauses. As a single insert condition is specified in the above query, it
applies to both the tables. You can give separate insert conditions for different
tables.




Conditional INSERT FIRST

Using the conditional INSERT FIRST statement you can insert selective values into
multiple tables. Multiple WHEN conditions are specified in this query. However, in
INSERT FIRST statement, if the first WHEN condition evaluates to true, the Oracle
server executes the corresponding INTO clause, and the subsequent WHEN
conditions for this row are skipped. If the first WHEN condition is not true, the
subsequent WHEN conditions are evaluated. Wherever the WHEN condition evaluates
to true, the corresponding INTO clause is executed.



© SQL Star International Ltd.                                                       398
For example if you want to perform conditional Multi-table insert using INSERT FIRST
  statement in the query, first, create the tables TransHistory99, TransHistory00
  and TransHistory. Insert the following values in the newly created tables:

         The transaction details of all members    who are due to pay a fine in
           TransMemberHistory table
         Details of transactions that took         place   in   the   year    1999   in   table
           TransHistory99
         Details of transactions that took         place   in   the   year    2000   in   table
           TransHistory00
         Details of transactions that took place   in the years other than 1999 and 2000
           in table TransHistory

  The    following  query   performs Multi-table insert                  into     the   tables
  TransMemberHistory, TransHistory99, TransHistory00                     and     TransHistory
  using INSERT FIRST statement.


           INSERT FIRST
           WHEN nFine IS NOT NULL THEN
                   INTO TransMemberHistory
                   VALUES (cTranID, cMemberID, cBookID, dIssueDt, nFine)
           WHEN dIssueDt LIKE (‗%99%‘) THEN
                   INTO TransHistory99
                   VALUES (cTranID, cMemberID, cBookID, dIssueDt, dActualReturnDt)


           WHEN dIssueDt LIKE (‗%00%‘) THEN
                   INTO TransHistory00
                   VALUES (cTranID, cMemberID, cBookID, dIssueDt, dActualReturnDt)
           ELSE
                   INTO TransHistory
                   VALUES (cTranID, cMemberID, cBookID, dIssueDt, dActualReturnDt)
                   SELECT cTranID, cMemberID, cBookID, dIssuedt, dActualReturnDt,
                   nFine
                   FROM Transaction;

32 rows created.



  Pivoting INSERT
  Suppose you retrieve a record from a non-relational database table and wish to store
  it in a relational format, you can do so with the help of an operation called Pivoting
  INSERT. Pivoting INSERT enables you to transform records retrieved from a non-

  © SQL Star International Ltd.                                                              399
relational database table into a relational format. This is done by converting the
retrieved record into multiple records and storing it in a manner that resembles a
relational database table environment.

For instance, the table StudentMarksDetail contains the details of marks scored by
students in all courses. It is a non-relational database table. When you select records
from this table, it gives the following output:

NSTUDENTNO       CCOURSEID       NOPSYS    NBDMS NARTINT           NPROGLANG
----------      ---------  ------   ----- ------- ---------
        101           SE01      80      75      85       90

As this record is retrieved from a non-relational database table, you can give it a
relation format by implementing Pivoting INSERT on it. Because of pivoting INSERT,
the marks for each subject in the course will be inserted as a separate row in the
StudentMarksInfo table. First create another table called StudentMarksInfo that
contains columns for student number, course ID and marks. Following is the query to
perform Pivoting INSERT:


       INSERT ALL
       INTO StudentMarksInfo values (nStudentNo, cCourseID, nOpSys)
       INTO StudentMarksInfo values (nStudentNo, cCourseID, nBDMS)
       INTO StudentMarksInfo values (nStudentNo, cCourseID, nArtInt)
       INTO StudentMarksInfo values (nStudentNo, cCourseID, nProgLang)


       SELECT nStudentNo, cCourseID, nOpSys, nBDMS, nArtInt, nProgLang
       FROM StudentMarksDetail;


       4 rows created.

When you execute this query, the student marks details are selected from the non-
relational database table StudentMarksDetail. The marks of the students in each
subject as operating systems, DBMS, Artificial Intelligence and programming
languages are inserted as separate records in StudentMarksInfo table. Thus, the
output from a non-relational database table is converted into a relational format.
When you select records from StudentMarksInfo table, following is the output:

       NSTUDENTNO CCOURSEID MARKS
       ——————— ——————— —————
          101     SE01   80
        101      SE01   75
        101      SE01   85
        101      SE01   90



Points to Remember: -

© SQL Star International Ltd.                                                      400
     Multi table inserts can only be performed on tables, not on views or
         materialized views.
        You cannot perform Multi-table inserts into nested tables.

        The sum of all the INTO columns cannot exceed 999.

        Sequences cannot be used in the subquery of the multi-table insert
         statement.



External Tables
External tables are read-only tables. Here data is actually stored outside the
database in flat files and only the metadata is stored in the database. If you want to
make a table as read-only, create it as an external table.

The Oracle server uses drivers to access the data from external files (stored outside
the database). However, with external tables you can perform only SQL queries. You
cannot perform DML operations (UPDATE/INSERT/DELETE) on external tables, nor
can you create indexes on them.

To access external tables, Oracle server provides two main access drivers:

       ORACLE_LOADER, for reading data from external table using the Oracle
         loader technology.
       ORACLE_INTERNAL, the import/export access driver used for importing and
         exporting of data using a platform independent format.

The data used by external tables is stored in data files stored under a directory.
Therefore, you must create a DIRECTORY object that corresponds to the directory on
the file system on which the data files reside. The syntax to create a directory object
is:

               CREATE [OR REPLACE] DIRECTORY AS ‗path_name‘;

Where,

CREATE, Allows you to create a new directory database object

REPLACE, Allows you to re-create or replace a directory object

DIRECTORY, Name of the directory object to be created, with a maximum length of
30 bytes. You cannot specify a schema name to a directory object.

‗path_name‘ Specifies the full path name of the directory on the server where the
data files are located. Single quotes indicate that the path name is case sensitive.

As the above command indicates, the ‗path_name‘ is an alias for the directory
object. Whenever this directory object is referenced, it actually refers to path where
the data files are located.


© SQL Star International Ltd.                                                      401
Create a directory object mem_dir in the following manner:

CREATE DIRECTORY mem_dir AS ‗ext_dat‘;

The directory object mem_dir specifies an alias for the directory on the file system
of the server, where the data files are stored.

Now create a data file called Members.txt containing the data about old members
of New Jersey Central Library in the following format :–
        A01010101,Anna,Jones,25-Nov-1995
        B02020202,Steve,Patterson,05-Oct-1994
        C03030303,Mark,Blair,12-Jan-1996


Observe the data in the file. The fields are delimited by a ‗,‘ and the records are
terminated by new-line. Save this file in the path ‘ext_datMembers.txt’.

To convert this datafile into a datasource for external tables, follow these steps:

   1.   You must first create three directory objects

       The default directory object as follows:
        CREATE OR REPLACE DIRECTORY memdir AS ‗d:ext_data‘;

       The log file directory object as follows:
        CREATE OR REPLACE DIRECTORY log_memdir AS ‗d:ext_data‘;

       The bad file directory object as follows:
        CREATE OR REPLACE DIRECTORY bad_memdir AS ‗d:ext_data‘;




© SQL Star International Ltd.                                                         402
2. Grant appropriate read – write permissions to the files stored in these
            directories

                 Only read permission to default directory:
                  GRANT READ ON DIRECTORY memdir TO scott;


                 Write permission to ‗log‘ and ‗bad‘ directories:
                  GRANT WRITE ON DIRECTORY log_memdir TO scott;
                  GRANT WRITE ON DIRECTORY bad_memdir TO scott;


         3. Connect to the user scott/tiger and create the external table.
             CONNECT scott/tiger;




Creating External Tables
Creating an external table is similar to creating a regular table, except for some additional clauses.

You must incorporate the following clauses in your code:

       CREATE TABLE clause with column names and their datatypes.
       ORGANIZATION EXTERNAL to indicate that the table is an external table and
         must be stored outside the database.
       The access driver type to indicate which driver will be used by the Oracle
         server to access data from data files.
       The DEFAULT DIRECTORY clause, that lets you specify one or more directory
         objects that correspond to the directories on the file system where the data
         files are stored. You can specify multiple default directories, as these are
         permitted to facilitate load balancing.
       ACCESS PARAMETERS, which are values specific to the access drivers used
         for this external table. These values are not interpreted by Oracle but by the
         access driver used to access data files.
       The LOCATION clause that allows you to specify one external locator (usually
         a data file) for each external data source. The access driver interprets this
         information and not the Oracle server.
       The PARALLEL clause specifies the number of execution servers to
         simultaneously scan the external data sources (files) during the execution of
         INSERT INTO TABLE statement.
       The REJECT LIMIT specifies how many conversion errors can occur while
         querying an external data before the Oracle server returns an error message
         and the query is aborted. By default, the REJECT LIMIT is zero.

The following code illustrates the use of all the aforesaid clauses and creates an
external table known as OldMembers:


         CREATE TABLE OldMembers

© SQL Star International Ltd.                                                                            403
(cMemberID char(9),
       cFirstName CHAR(20),
       cLastName CHAR(20),
       dMembershipDt DATE
      )
       ORGANIZATION EXTERNAL
       (
           TYPE ORACLE_LOADER
           DEFAULT DIRECTORY memdir
           ACCESS PARAMETERS
           (
           RECORDS DELIMITED BY NEWLINE
           BADFILE bad_memdir:‘memXt%a_%p.bad‘
           LOGFILE log_memdir:‘memXt%a_%p.log‘
           FIELDS TERMINATED BY ‗,‘
           MISSING VALUES ARE NULL
               (cMemberID CHAR, cFirstName CHAR,
                   cLastName CHAR, dMembershipDt CHAR
               date_format date mask ―dd-mon-yyyy‖
               )
           )
           LOCATION (‗Members.txt‘)
       )
       PARALLEL 5
       REJECT LIMIT 200;


In the above code, the Keywords ORGANIZATION EXTERNAL indicates that the table
to be created is an external table which stores data for member ID, first name, last
name and membership date. TYPE ORACLE LOADER specifies the access driver. The
default directory is memdir. The code also specifies the log directory and the bad
directory. The ACCESS PARAMETERS specify the format of the data file. LOCATION
specifies the name of the flat file where the data is actually stored. PARALLEL 5
specifies that five server process can simultaneously execute. The REJECT LIMIT is
200, indicating that 200 errors can occur before the query is aborted.

When you execute the above code successfully, it creates the external table
OldMembers.
      Table created.


© SQL Star International Ltd.                                                   404
Now when select the data from external table OldMembers, the driver ORACLE_LOADER looks for the
data file Members.txt in the path ‘d:ext_data’ specified by the default directory memdir, fetches the
data from Members.txt file and displays it as follows:

            CMEMBERID CFIRSTNAME CLASTNAME DMEMBERSH
            --------- ---------- --------- ---------
            A01010101         Anna         Jones                 25-NOV-95
            B02020202         Steve        Patterson 05-OCT-94
         C03030303            Mark         Blair        12-JAN-96
Unloading Data Using External Tables in Oracle10g

Oracle10g has taken external tables a stage further by enabling an external table to
be created as a CTAS ( Create Table As Select ) operation, which enables a one-time
unloading of data. Oracle has in fact supplied a new access driver known as
―ORACLE_DATAPUMP‖ which means that Oracle will ―unload‖ an external table to a
proprietary format usable by the Data Pump set of utilities (significant new 10g
feature to replace imp and exp). So, generating an ASCII, CSV file from external
tables is not possible, but this new feature is exciting nonetheless. The above feature
is demonstrated with a sample example below.

Step 1: Create a directory

         SQL> CREATE DIRECTORY mydir AS ‗/oracle/opt‘;

Step 2: Provide permission to one of the users say scott.

          SQL> GRANT READ, WRITE ON DIRECTORY mydir TO scott;

Step 3: Create the external table.


        CREATE TABLE demotab
             ORGANIZATION EXTERNAL
             (TYPE ORACLE_DATAPUMP default directory mydir
             LOCATION (‗book_category.exp‘))
             AS
             SELECT b.cBookname, b.cAuthorname, c.cCategoryname
                  from Book b, Category c
             WHERE b.cCategoryid=c.cCategoryid;



and we will find a file generated book_category.exp in ‗/oracle/opt‘ directory. We can
take this file to the target database and create an external table for that.



Merging Rows


© SQL Star International Ltd.                                                                    405
Merging rows enables you to use the UPDATE and INSERT statements in the same
query. The MERGE statement (also called ―upsert‖) is an extension of the existing
SQL statements. The MERGE statement allows you to conditionally update and insert
rows in a table. If the row exists, it updates it, else, inserts it into the table.

You can perform these activities using PL/SQL loops and multiple DML statements.
However, MERGE is easier to use and can be written as a single SQL statement.

The MERGE statement avoids the use of multiple UPDATE statements, requiring few
scans of the source table, and thereby improving performance. This concept is
particularly useful in data warehousing, where data may be inserted from multiple
sources. There can be duplicates. If the row exists, it will be updated, else it will be
added.




For MERGE statements, you need two tables, a source table and a target table. Using
MERGE, you can not only update the values in the target table with the values in the
source table but also add new rows from the source to the target table.

You must have the INSERT and UPDATE object privileges on the target table and the
SELECT object privilege on the source table. To specify the DELETE clause of the
merger_update_clause, you must also have the DELETE object privilege on the
target table.

The MERGE statement is deterministic. You cannot update the same row of the
target table multiple times in the same MERGE statement.

For instance, if you wish to update the phone numbers in the Member table
(target), with the phone numbers in the MemberSrc table (source), use the query
given below. The MemberSrc table contains a new row for member ‗Allen Scott‘.
The Member table does not contain this row. When you issue a MERGE statement,
the new row is inserted into the Member table. This is the advantage of using a
MERGE statement, where you can update and insert the rows using a single query.
You need not use multiple queries.




       MERGE INTO Member M USING Membersrc S
       ON (m.cMemberID = S.cMemberID)
       WHEN MATCHED THEN


© SQL Star International Ltd.                                                       406
UPDATE SET m.cPhone=s.cPhone
       WHEN NOT MATCHED THEN
              INSERT VALUES(s.cMEmberID, s.cFirstName,
              s.cLastName, s.vAddress, s.cArea,
              s.cZipcode, s.cPhone, s.nAge, s.dMembershipDt,
              s.cGrade, s.cMaritalStatus, s.cBranchID);


In the query, first the member IDs of the source and the target are matched. If they
match, the phone number in the Member table is updated with the values in the
MemberSrc table. If the member IDs do not match (meaning the row does not
exist), the row is inserted into Member table.

In Oracle10g use of WHEN MATCHED AND WHEN NOT MATCHED clause is made
optional. Also, you can restrict the values while inserting into target table using
WHERE CLAUSE.

For example the above can be slightly modified to insert only those members whose
age is greater than 10.


       MERGE INTO Member M USING Membersrc S
       ON (m.cMemberID = S.cMemberID)
       WHEN NOT MATCHED THEN
              INSERT VALUES(s.cMEmberID, s.cFirstName,
              s.cLastName, s.vAddress, s.cArea,
              s.cZipcode, s.cPhone, s.nAge,
              s.dMembershipDt, s.cGrade, s.cMaritalStatus, s.cBranchID)
              WHERE S.NAGE>10;


Oracle10g Flashback enhancements

Oracle 10g provides two enhancements to flashback query, namely,

   1. Flashback version query

   2. FLASHBACK_TRANSACTION_QUERY VIEW

The flashback version query feature let‘s us see the table data as it changed over
time. We request the 10g database to show us all versions between two points in
time (in the form of time stamps) or between the two system change numbers
(SCN‘s). This feature requires that the undo records for the transaction that changed
the table data are available.

The concept of a ‗version‘ of a row is transaction based. A version is created when a
transaction involves row commits. So, if there have been 10 transactions that

© SQL Star International Ltd.                                                    407
changed the row and 8 were committed – between yesterday and today, and you
request all versions of that row in that time period, you will see 8 rows of output-
one for each version. Changes that were rolled back do not generate a version.

Use the VERSIONS BETWEEN CLAUSE to code a ―flashback version query‖.
Oracle 10g supports MINVALUE and MAXVALUE in the VERSIONS BETWEEN clauses.
These expressions give access to the oldest and most recent data available.

Example of the flashback version query

       SELECT nFine FROM Transaction WHERE cTranid=‘T0000290100‘;

Assume the output gives 15

       UPDATE Transaction SET nFine=nFine+0.10 WHERE cTranid=‘T0000290100‘;

Now nfine is 15.1.

Now commit the above transactions using COMMIT command.

Now execute the following statement:
     SELECT nFine FROM Transaction VERSIONS BETWEEN SCN MINVALUE AND
MAXVALUE
       WHERE cTranid=‘T0000290100‘;
Now the output will be 15 and 15.1.




FLASHBACK_TRANSACTION_QUERY VIEW

It is easy to see the changes made to the tables with flashback_transaction_query
view. This can be helpful for auditing (i.e. who changed my table), debugging and
even performance analysis (how often is a table being changed).

The SELECT ANY TRANSACTION privilege allows the user to query the past
transaction by querying the above-mentioned view.




© SQL Star International Ltd.                                                   408
Summary
In this chapter, you have learnt that:

    Multi-table insert allows you to insert rows into multiple tables as a part of a
   single DML statement. These are designed with regard to data warehousing
   system.
       There are four types of Multi-table INSERT statements:

                Unconditional INSERT
                Conditional INSERT ALL
                Conditional INSERT FIRST
                Pivoting INSERT

    External tables are read only tables whose data is stored in a flat file. It
   stores only the metadata information in the database.

    MERGE statement is used to perform the insertion and updation as a single
   operation in the same statement. In Oracle10g, condition merging can be
   performed.

    The flashback version query feature let‘s us see the table data as it changed
   over time.

    FLASHBACK_TRANSACTION_QUERY VIEW helps us to get information for
   auditing, debugging and statistic analysis.




© SQL Star International Ltd.                                                    409
Lab Exercise

[Note: For questions 1 to 2, you are required to work with SalHistory,
ManagerHistory, SpecialSalary, SpecialSalHistory, HireDt00, HireDt99 and
HireDt_History tables.]

To work with these tables, you need to run the script file LabEx18_01.sql.
The structures of these tables are given below.

Structure of SalHistory




Structure of ManagerHistory




Structure of SpecialSalary




Structure of SpecialSalHistory




Structures of HireDt00, HireDt99, and HireDt_History are the same




© SQL Star International Ltd.                                                410
1.      Write a query to retrieve the employee ID, manager ID, hire date, and salary
of those employees whose employee ID is less than or equal to 115. Use the query
result set to do the following:


       Insert into the SpecialSalary table the employee ID and salary of those
employees who earn a salary of more than $15,000. In case salary is less than
15,000, do the following:
                  Insert into the SalHistory table the employee ID, hire date,
                        and salary.
 Insert into the ManagerHistory table the employee ID,
                        manager ID, and salary.
      Confirm the rows created in all the three tables.

2.            Write a query to retrieve the department ID, sum of salary, and maximum
hire date, which are grouped according to the department ID. Use the result set to
perform the following:

     Insert department ID and salary into the SpecialSalHistory table if the
sum of salary happens to be greater than $20,000. Use conditional FIRST Multi-table
INSERT.

    In case the first WHEN clause returns TRUE, skip the subsequent WHEN
clauses for this row.

   In case of the rows that do not satisfy the first WHEN clause, insert into:

                      HireDt00 table if hire date year is 2000
                      HireDt99 table if hire date year is 1999
                      HireDt_History table for all other hire dates

             Confirm the rows created in the above tables.

[Note: For question 3, you are required to work with SalesInfoFile and SalesInfo
tables.]

3.      To create these tables run the script file LabEx18_03.sql. To insert records
into the SalesInfoFile table run the script file LabEx18_03a.sql.

Structure of SalesInfoFile




© SQL Star International Ltd.                                                            411
SalesInfoFile table data




Structure of SalesInfo




Write a query to retrieve the employee ID, week ID, and sales figures on Monday,
Tuesday, Wednesday, Thursday, and Friday from the SalesInfoFile table such that
the records retrieved are converted into multiple records for the SalesInfo table.
Confirm the records inserted into SalesInfo table.


4.      Create an External Table called All_objects_Xt, dump data into a .txt file.
        Select the data from all_objects data dictionary.
       Query the external table

5a.     Create a table Tax with the below given two columns:
        Salary NUMBER(10)
        Tax_Rate NUMBER(15,5)

5b.     Insert 1 row into them with values 20000,10.
        Commit it
        Update the Tax_rate with 0.15.
        Commit it
        Increase the Tax_rate further with 0.20.
        Commit it
        Delete the row from the table.
        Commit it

        Insert 1 row into the table with values 20000,25.
        Commit it
        Update the Tax_rate with 0.27.

© SQL Star International Ltd.                                                     412
Commit it

6.    Write a query to select the prevailing tax rate from the table.

7.    Write a query to list all the changes made to the Tax table.

      What enhancement has been made in External table.




© SQL Star International Ltd.                                           413
Chapter 19




                                 REGULAR EXPRESSION
                                Overview of Regular Expression Support
                                                List of Meta-characters
                                          Regular Expression Functions




© SQL Star International Ltd.                                      414
Objectives

At the end of this chapter, you will be able to:

     Use meta-characters

     Use regular expression functions

     Use NOVALIDATE Clause




© SQL Star International Ltd.                      415
Introduction to REGULAR EXPRESSION
In Oracle Database 10g, additional meta-characters have been introduced; in an
attempt to make the search, compare and replace functions operate in a more
intensified manner, than it is in Unix and Java. These functions are known as regular
expressions that has made matching complex text pattern more effective. It follows
Portable Operating System For Unix (POSIX) standard for matching ASCII
characters.

With this new feature, most of the complex search requirements of the end users can
be addressed.

META-CHARACTER
These are special characters with pre-defined meaning that are used in our
complex string-matching pattern.

Following is the list of Meta-Characters that are used for String Searching.




© SQL Star International Ltd.                                                    416
Below are the various comparisons for the Character class, which is used in complex
string searching.




© SQL Star International Ltd.                                                  417
Regular Expression Functions
Oracle Database 10g has come up with 4 new functions which use meta-characters
in their arguments to help us accomplish our complex string pattern matching task.
The Searched String is to be enclosed in single quotation marks. These functions are
primarily an extension to our basic SQL functions with little variations.

Following are the list of Functions introduced in Oracle10g:

REGEXP_LIKE
Looks for a matching pattern in a character column.
It takes two arguments. First argument is the name of the character column. Second
argument is a regular expression string.

Following is an example of the syntax for this function: -

                          REGEXP_LIKE(srcstr, pattern [,match_option])

In this example, ‘ Names of the Members are extracted who have ‗at‘ in their
firstname‘.
            SELECT cFirstName
            FROM member
                          WHERE REGEXP_LIKE (cfirstname,’(at)’);
       Displays:
                          CFIRSTNAME
                          ----------
                          Katya
                          Kathy


REGEXP_REPLACE
Looks for a matching pattern in a character column and replaces each occurrence of
that pattern with the specified pattern.

The syntax for this is:


            REGEXP_REPLACE(srcstr, pattern [,replacestr [, position
               [, occurrence [, match_option]]]])

In this example, two spaces are replaced by a single space in a string.


       SELECT REGEXP_REPLACE(‗NEW           JERSEY   LIBRARY   STORES ‗,
       ‗( ){2,}‘, ‘ ‗) ―REGEXP_REPLACE‖
              FROM DUAL;
Displays:
      REGEXP_REPLACE
© SQL Star International Ltd.                                                    418
------------
      NEW JERSEY LIBRARY STORES



REGEXP_INSTR

This function searches a string for a given occurrence of a regular expression
pattern. You can specify which occurrence you want to find and the start position.



Syntax :

             REGEXP_INSTR (srcstr, pattern [, position [, occurrence
    [, return_option [, match_option]]]])


Example given below shows the position of @ in a given email id.


       SELECT REGEXP_INSTR(email,‘@{1}‘) ―Position‖ FROM MEMBER;
Displays:
       Position
    --------
       12



REGEXP_SUBSTR

This is similar to REGEXP_INSTR but instead of the position of the specified pattern it
returns a part of a string after matching the regular expression pattern.

Following is the syntax: -


               REGEXP_SUBSTR (srcstr, pattern [, position [, occurrence

      [, match_option]]])


Example to extract the username from the email of the members of New Jersey
Central Library:




           SELECT REGEXP_SUBSTR(member_email, ‗[^@]+‘)
            FROM     Member;


Explanation for the words used in the Syntax

© SQL Star International Ltd.                                                      419
Srcstr:- Indicates the Search value that can be an expression or a character column
name.
Pattern:- Regular expression
          replacestr:- Character String replacing pattern.
Position:- Starting position to Search from.
Occurrence:- Number of Occurrences to search for.
Return_option:- Beginning or Ending position of occurrence
Match_option:-Option to change default matching; it can include one or more of the
following values:
        “c” —uses case-sensitive matching (default)
        “I” —uses case-insensitive matching
        “n” —allows match-any-character operator
        “m” —treats source string as multiple line


Validating Data using Constraints

These multilingual regular expression functions can be included in CHECK constraint,
which prevent invalid data from being entered.

To make the checking‘s on the subsequent data only, NOVALIDATE clause can be
specified.

To check that cMemberid should start with ‗M‘ only, the following code should be
executed.


     ALTER TABLE Member
     ADD CONSTRAINT e CHECK(REGEXP_LIKE (cMemberid,‗^M‘))NOVALIDATE;


Here ‗^M‘ expression checks for the Member id starting with ‗M‘. NOVALIDATE clause
ensures that only subsequent entries of data are validated.




© SQL Star International Ltd.                                                      420
Summary

In this chapter, you have learnt that:

     Regular expression works beyond the Portable Operating System For Unix
        (POSIX) Standard.

 It helps us to perform complex string matching operation.

      New meta-character symbols have been introduced for string
        matching operation.

 New Functions such as REGEXP_LIKE(for comparison), REGEXP_REPLACE(for
        Replacing), REGEXP_INSTR(for finding position of a character),
        REGEXP_SUBSTR                                                       (returns
        part of a string) are introduced to accomplish our complex string pattern
        matching task.




© SQL Star International Ltd.                                                    421
Lab Exercise

1. A string contains three spaces in between. For example ‗NEW      DELHI‘. Write a
   query to replace the spaces with one. The output displayed should be as
   NEW DELHI
2. Write a query, which extracts a part of a string. The regular expression searches
for a comma followed by a space; then zero or more characters that are not
commas, as indicated by [^,]*; and lastly looks for another comma.
The pattern will look similar to a comma-separated values string.
(‗first part, second part, third part‘)
3. Retrieve any values from ename that start with J, followed by any letter, then
N or M, then any letter, then S from Emp table




© SQL Star International Ltd.                                                         422

More Related Content

PDF
Database Performance Management in Cloud
PPTX
DATABASE ADMINSTRATION
DOC
PDF
Handy annotations-within-oracle-10g
PPTX
1 introduction
PDF
Rdbms Practical file diploma
PDF
Oracle Optimized Datacenter - Storage
DOCX
Satwinder SQL.SSK_Brd_2015
Database Performance Management in Cloud
DATABASE ADMINSTRATION
Handy annotations-within-oracle-10g
1 introduction
Rdbms Practical file diploma
Oracle Optimized Datacenter - Storage
Satwinder SQL.SSK_Brd_2015

What's hot (20)

PDF
Sybase job interview_preparation_guide
DOC
Ramesh_Oracle_DBA
DOC
5-Ashutosh_resume
DOCX
CV_Masood Ahmad_1110
PPS
Ado.net session10
DOCX
Suresh Kumar
PDF
Rise of NewSQL
PDF
SQL Server Integration Services with Oracle Database 10g
DOCX
DBMS FOR STUDENTS MUST DOWNLOAD AND READ
PDF
Sql server difference faqs- 6
PDF
Sigmod 2013 - On Brewing Fresh Espresso - LinkedIn's Distributed Data Serving...
PPT
2ndlec.database
PPTX
Ebook1
DOCX
NeilResume
PDF
Oracle database 12c sql worshop 2 student guide vol 2
PDF
Partitioning 11g-whitepaper-159443
PPTX
DEE 431 Introduction to Mysql Slide 3
PDF
Twp partitioning-11gr2-2009-09-130569
PPTX
Database design challenges conflicting goals
PDF
DBArtisan XE6 Datasheet
Sybase job interview_preparation_guide
Ramesh_Oracle_DBA
5-Ashutosh_resume
CV_Masood Ahmad_1110
Ado.net session10
Suresh Kumar
Rise of NewSQL
SQL Server Integration Services with Oracle Database 10g
DBMS FOR STUDENTS MUST DOWNLOAD AND READ
Sql server difference faqs- 6
Sigmod 2013 - On Brewing Fresh Espresso - LinkedIn's Distributed Data Serving...
2ndlec.database
Ebook1
NeilResume
Oracle database 12c sql worshop 2 student guide vol 2
Partitioning 11g-whitepaper-159443
DEE 431 Introduction to Mysql Slide 3
Twp partitioning-11gr2-2009-09-130569
Database design challenges conflicting goals
DBArtisan XE6 Datasheet
Ad

Viewers also liked (12)

PPTX
Machine Learning on the Microsoft Stack
PPTX
SSDT unleashed
PPSX
SQL Reporting service presentation
PPTX
Introduction of ssis
PPT
Introduction To Msbi By Yasir
PPTX
SQL Server Reporting Services (SSRS) 101
PPTX
SQL Server Reporting Services
PPT
MSBI-SSRS PPT
PPT
SSIS Presentation
PPTX
Introduction to MSBI
PPTX
SQL Server Integration Services
PPTX
Getting Started with SQL Reporting Services Webinar
Machine Learning on the Microsoft Stack
SSDT unleashed
SQL Reporting service presentation
Introduction of ssis
Introduction To Msbi By Yasir
SQL Server Reporting Services (SSRS) 101
SQL Server Reporting Services
MSBI-SSRS PPT
SSIS Presentation
Introduction to MSBI
SQL Server Integration Services
Getting Started with SQL Reporting Services Webinar
Ad

Similar to 10g sql e book (20)

PPT
Ebook10
PPT
Sql interview question part 10
PPTX
NCTU ppt 2023-2024_WEEK1-Introduction to DBMS.pptx
PPTX
Database management system
PPTX
Sql interview question part 5
PPTX
Ebook5
DOCX
Report 1.0.docx
PDF
A STUDY ON GRAPH STORAGE DATABASE OF NOSQL
PDF
A Study on Graph Storage Database of NOSQL
PDF
A Study on Graph Storage Database of NOSQL
PDF
A STUDY ON GRAPH STORAGE DATABASE OF NOSQL
PDF
Why Should you choose SQL Server 2019 ?
PDF
SQL RDBMS Database System (Modern) Features & Types
PDF
An Overview of Data Lake
PDF
Data Base
PPTX
No sql database
PDF
58750024 datastage-student-guide
PDF
Financial, Retail And Shopping Domains
PDF
10 Steps Optimize Share Point Performance
PDF
Migration to Oracle 12c Made Easy Using Replication Technology
Ebook10
Sql interview question part 10
NCTU ppt 2023-2024_WEEK1-Introduction to DBMS.pptx
Database management system
Sql interview question part 5
Ebook5
Report 1.0.docx
A STUDY ON GRAPH STORAGE DATABASE OF NOSQL
A Study on Graph Storage Database of NOSQL
A Study on Graph Storage Database of NOSQL
A STUDY ON GRAPH STORAGE DATABASE OF NOSQL
Why Should you choose SQL Server 2019 ?
SQL RDBMS Database System (Modern) Features & Types
An Overview of Data Lake
Data Base
No sql database
58750024 datastage-student-guide
Financial, Retail And Shopping Domains
10 Steps Optimize Share Point Performance
Migration to Oracle 12c Made Easy Using Replication Technology

Recently uploaded (20)

PPTX
Cell Structure & Organelles in detailed.
PDF
Computing-Curriculum for Schools in Ghana
PPTX
school management -TNTEU- B.Ed., Semester II Unit 1.pptx
PPTX
Pharmacology of Heart Failure /Pharmacotherapy of CHF
PDF
BÀI TẬP BỔ TRỢ 4 KỸ NĂNG TIẾNG ANH 9 GLOBAL SUCCESS - CẢ NĂM - BÁM SÁT FORM Đ...
PDF
Saundersa Comprehensive Review for the NCLEX-RN Examination.pdf
PDF
Anesthesia in Laparoscopic Surgery in India
PDF
Supply Chain Operations Speaking Notes -ICLT Program
PDF
Abdominal Access Techniques with Prof. Dr. R K Mishra
PDF
O5-L3 Freight Transport Ops (International) V1.pdf
PDF
102 student loan defaulters named and shamed – Is someone you know on the list?
PPTX
PPT- ENG7_QUARTER1_LESSON1_WEEK1. IMAGERY -DESCRIPTIONS pptx.pptx
PDF
The Lost Whites of Pakistan by Jahanzaib Mughal.pdf
PPTX
Introduction_to_Human_Anatomy_and_Physiology_for_B.Pharm.pptx
PDF
01-Introduction-to-Information-Management.pdf
PPTX
GDM (1) (1).pptx small presentation for students
PDF
Microbial disease of the cardiovascular and lymphatic systems
PDF
Insiders guide to clinical Medicine.pdf
PDF
2.FourierTransform-ShortQuestionswithAnswers.pdf
PDF
TR - Agricultural Crops Production NC III.pdf
Cell Structure & Organelles in detailed.
Computing-Curriculum for Schools in Ghana
school management -TNTEU- B.Ed., Semester II Unit 1.pptx
Pharmacology of Heart Failure /Pharmacotherapy of CHF
BÀI TẬP BỔ TRỢ 4 KỸ NĂNG TIẾNG ANH 9 GLOBAL SUCCESS - CẢ NĂM - BÁM SÁT FORM Đ...
Saundersa Comprehensive Review for the NCLEX-RN Examination.pdf
Anesthesia in Laparoscopic Surgery in India
Supply Chain Operations Speaking Notes -ICLT Program
Abdominal Access Techniques with Prof. Dr. R K Mishra
O5-L3 Freight Transport Ops (International) V1.pdf
102 student loan defaulters named and shamed – Is someone you know on the list?
PPT- ENG7_QUARTER1_LESSON1_WEEK1. IMAGERY -DESCRIPTIONS pptx.pptx
The Lost Whites of Pakistan by Jahanzaib Mughal.pdf
Introduction_to_Human_Anatomy_and_Physiology_for_B.Pharm.pptx
01-Introduction-to-Information-Management.pdf
GDM (1) (1).pptx small presentation for students
Microbial disease of the cardiovascular and lymphatic systems
Insiders guide to clinical Medicine.pdf
2.FourierTransform-ShortQuestionswithAnswers.pdf
TR - Agricultural Crops Production NC III.pdf

10g sql e book

  • 1. Oracle 10g SQL This book belongs to Name : ______________________________________ Batch : ______________________________________ SQL Star International Ltd. SQL Star House, No. 8-2-293/174/A 25, Road No. 14, Banjara Hills, Hyderabad - 500 034, Andhra Pradesh, INDIA © SQL Star International Ltd.
  • 2. Copyright © 2008 Second Edition SQL STAR INTERNATIONAL LIMITED SQL Star House,8-2-293/174/A25, Road No.14, Banjara Hills, Hyderabad - 500 034. Tel. No. 91- 40-23101600(30 lines) Fax No. 23101663 Toll Free No: 1800 425 2944 Email: info@sqlstar.com No part of this publication may be reproduced (incl. photocopying) in any way, without prior agreement and written permission of SQL Star International Ltd., Hyderabad. SQL Star International Ltd., Hyderabad assumes no responsibility for its use, nor for any infringements of patents or other rights of third parties which could result. © SQL Star International Ltd. i
  • 3. Table of Contents Oracle 10g SQL CHAPTER CHAPTER TITLE PAGE No. NO 1. Database concepts 1-39 2. Introduction to Oracle 10g 40-49 3. Data Retrieval 50-78 4. Enhancing Data Retrieval 79-95 5. Generating formatted reports using isql*plus 96-128 6. SQL single Row Functions 129-154 7. Working with Grouped Data 155-163 8. Joins 164-186 9. Understanding Sub queries 187-201 10. Advanced Sub queries 202-221 11. Data Manipulation 222-248 12. Managing Tables 249-293 13. Managing Constraints 294-318 14. Views 319-342 15. Other Database Objects 343-371 16. Data Dictionary Views 372-380 17. Security Implementation 381-393 18. Manipulating Large Data Sets 394-413 19. Regular Expressions 414-422 © SQL Star International Ltd. ii
  • 4. Chapter 1 Database Concepts Typical Database Architecture DBMS Types of DBMS Normalization Entity Relationship (E-R) Model Features of SQL © SQL Star International Ltd. 1
  • 5. Objectives At the end of this chapter, you will be able to: Understand the basic concepts of a database Identify the disadvantages with Flat File systems Identify the advantages of a DBMS Understand the types of DBMS Understand the E-R Model Understand the features of SQL Describe the Codd‘s Rules © SQL Star International Ltd. 2
  • 6. Database Management The approach of the new millennium has brought with it several challenges, thereby making it mandatory for companies and organizations to maintain high level of efficiency in their computing systems, so as to stand the test of time. Databases and database systems are the essential backbone of any organization. Database When one hears the word Database, one thinks of a collection or a store of mutually related data. The implicit properties of a database are as follows:  A database represents some aspects of the real world and any changes to the real world should get reflected in the database. For example, a manufacturing concern keeps details of the products it manufactures and also of the suppliers it deals with. Any change in the pricing of the product or a change in the suppliers who supply raw materials must be immediately reflected in the database.  A database is a logical collection of relevant data, reflecting some inherent meaning. Any random grouping of data cannot be referred to as a database. A manufacturing concern requires data about its customers, products, as well as its suppliers. Details regarding each of them form a logical group of data.  A database is populated with data for a purpose. It has an audience that is interested in its contents. For instance, in the above example, the manufacturing concern needs the customer details to identify its regular customers and also their credit worthiness. Similarly product detail helps in determining the stock depletion level (i.e. when to place fresh order for raw materials). Now a day, the term „database‟ is mostly used in connection with computerized databases. Therefore, today, a study of database systems involves also a study of the associated technology employed to store, access and manipulate the computerized databases. Traditionally, data accessed through computers has been stored on different storage media in the form of individual files. Files proved to be quite satisfactory as long as computerization was limited to a few application areas and the use of computers restricted to a privileged few. However, as actual users grew in number, especially with the advent of online time-sharing systems, the file systems gave rise to many serious problems. The discipline of database systems evolved in response to these problems. Let us first consider what these problems are so as to understand the different features of database systems more clearly. File Systems and the Associated Problems Most data processing systems in existence today, especially in India, use files for storing, accessing and manipulating data. Files are stored typically on magnetic tapes and disks. © SQL Star International Ltd. 3
  • 7. Most of the problems with files arise out of the fact that files are specific to an application, e.g., a set of files may be designed for the sales analysis system of a company. Programs of the same application system can use these files. However, if some other new application needs source data from this system, there may be difficulties. Therefore, in many cases, new files, with considerable data in common with the existing files, may have to be designed for the new applications. Therefore, as applications proliferate, the total number of computerized files grows considerably. Also, as the number of actual users of the computer grows, the number of applications increases, in turn resulting in an increase in the number of files. A large number of files give rise to the following problems:  Files involve a high level of redundancy in data. As we have mentioned above, proliferation of files results in the same data item being stored at many different places.  Redundancy in data often results in inconsistency of data. The same data item being used by different applications may exist in different versions. What is worse, it may exist in different stages of update at different places and thus may have different values. This may ultimately result in inconsistencies amongst reports generated by the two application systems.  Individual files are not amendable to rapid changes, especially with respect to the way the data items are structured within the file. If an application wants data from an existing file but structured differently, it cannot be provided quickly and easily. For this purpose, either conversion programs have to be written or new files have to be created.  Because of the inflexibility of files, many ad hoc queries cannot be answered.  Yet another consequence of the inflexibility of files is that it is usually expensive to make changes to a file system. It is also a very slow process. It may even involve modification of application programs.  What is worse, modification in one program may require modifications in other programs, which interface with this program. This process may set off a chain reaction of modifications. The above problems give rise to further difficulties detailed below:  The Management Information Systems (MIS) finds it difficult to control data, especially when the actual users develop applications on their own.  Major changes required in the system while modifying files increase the maintenance load on Data Processing (DP) professionals substantially, thus making them unavailable for development of new systems.  High-level data redundancy entails repetitive data entry and redundant storage with the accompanying costs. © SQL Star International Ltd. 4
  • 8. As has been already stated, Database Systems provide an effective solution to the above problems. Let us see how. Data Independence You have just seen, files give rise to several problems because they are application specific. Consequently, the applications become data-dependent, that is, they depend upon the organization and access method for the data on the secondary storage. This happens because, with conventional application development tools such as COBOL, the application logic incorporates the knowledge of data organization and access methods. Therefore, most changes in data organization or access methods affect the application logic substantially. If problems arising due to this fact are to be avoided, the data organization (and the access method) and the application logic have to be made independent of each other. Database Systems do precisely this. The first step towards this goal is to distinguish between data as is actually stored (called as the physical representation of data) and data as is presented to an individual user (called as the logical representation of data). The Physical Representation of Data The smallest named unit of data physically stored in the database is known as a ―stored field‖, and a named collection of associated stored fields is known as a ―stored or physical record‖. The named collection of all occurrences of one type of physical record is known as a ―stored or a physical file‖. This concept will be clearer after we discuss the logical representation of data. The Logical Representation of Data A logical field, record or file is, the field, record or file as it appears to the users, that is, as it is defined in the user‘s application programs. In all traditional systems, the logical and physical data are practically the same, which is the root cause of all the major problems with traditional files. This is not the case with database systems. Similarly, the structure of stored and logical records can be different. A logical record type may be obtained by selectively combining fields from different stored records. The logical and physical views of a file could also be different in terms of, say, the key fields for sequencing the records in the file. With such a separation of the logical and physical data, the database can be modified and developed without affecting existing applications. The database architecture achieves this separation. A Typical Database System Typical database architecture divides the database into three levels of abstraction; the internal, conceptual and external levels. At the internal level is the physical database, while at the external level; one has the different logical views corresponding to an individual application. The conceptual level is an intermediate level, which is a single abstract representation of the entire database. © SQL Star International Ltd. 5
  • 9. Data Base Management System (DBMS) is software, which interacts with all the three levels enabling the users to deal with the data in terms of its logical view rather than the actual physical database. A diagrammatic representation of the typical database architecture is shown below: Let us now consider the different individual entities in the architecture in further detail. Let us start with the actual or physical database and see how the architecture brings about a transformation in the data representation to get the data to the user in the form he wants. The Internal Database The internal (or physical) database is stored on secondary storage devices, mainly the magnetic disk. It itself can be conceptually viewed at different levels of abstraction. At its lowest level, it is stored in the form of bits with the associated physical addresses on the secondary storage device. At its highest level, it can be viewed in the form of files and simple data structures. It is this level that we shall study when we discuss the physical organization for databases in later chapters. © SQL Star International Ltd. 6
  • 10. The physical database is described by means of a physical scheme or an internal scheme. It essentially describes the various types of stored records, the different indexes that are employed for accessing these and the representations for different stored fields. It is also called as the ―storage structure definition‖. The Conceptual Database The conceptual model, also called as the data model, represents information content of the database in its entirety, but is abstract with respect to the physical database. Broadly speaking, the conceptual model provides a view of the data as it really is. This model consists of multiple occurrences of multiple types of a conceptual record. A conceptual record represents relevant information content only. In this sense, it is much closer to the external record than a stored record is. However, it is not the same as the external record. It contains all the information to build relevant external records. A conceptual stock record may consist of the quantity of material and the buying rate but not its value; still the user‘s external record may consist of the value of the stock. A conceptual model may consist of occurrences of such stock records, a collection of supplier record occurrences and a collection of assembly records. Obviously, the conceptual model is derived from the physical model. For this, the database needs a conceptual/physical mapping, which specifies how conceptual records and fields map into their counterparts in the physical database. The conceptual database is described by means of a conceptual scheme. Needless to say, the conceptual scheme is independent of the physical characteristics of data, such as storage structures, physical sequences, stored field representations etc. Ideally the conceptual scheme should include many features in addition to just the definitions of conceptual records. These may include relevant authorization checks and validation procedures, the uses of data, the source and destination of data etc. The conceptual database is a real-world view of data from the organization point of view. As the real world changes, changes have to be made to the conceptual database and scheme as well. In such a case, it is usually possible to limit the corresponding changes to only those external schemes, which use the conceptual elements that are changed. The External Database The external model (or view) is application-specific. Therefore, the user views the database through an external model, and there are as many external views as there are applications. External views are the proper interface between the user and the database as an individual user can hardly be expected to be interested in the entire database. Generally, an external model consists of multiple occurrences of multiple types of external record. An example of an external record is the record of a file as defined in the data division of COBOL program. Each external model is defined by means of an external scheme, which describes each external record type in the external model. The external model is derived from the conceptual model. For this purpose, the correspondence between the particular external models has to be defined. An © SQL Star International Ltd. 7
  • 11. external/conceptual mapping similar to the conceptual/physical mapping does this. However, a separate mapping has to be defined for each external view. An explicit definition of the mapping should be documented, preferably in the corresponding external scheme. The user interacts with the database through a high-level language such as COBOL, PL/I or some special purpose language. This language is known as the host language. It includes a data sub-language (DSL). The user carries out the retrieval and storage operations on the database through the DSL. In fact, the Database Task Group (DBTG) report published in April 1971, contains proposals for three distinct languages, two of which relate very closely to the concept of a DSL. These are sub scheme Data Description Language (DDL) and Data Manipulation Language (DML). The sub scheme DDL is used for defining the external views while the DML is used for carrying out operations on the database. In addition to the languages, the user is also supposed to be provided with a workspace. This workspace is an area meant for receiving or transmitting all data transferred between the user and the database. This is simply the input-output area for a program. Let us now consider what a database management system is, which interacts with the three levels and the mappings. What is a Database Management System? The DBMS is the software, which handles all accesses to the database. Conceptually, if a user requests a certain data item, the DBMS intercepts and interprets the request, retrieves the relevant stored occurrences from the physical database, constructs the required conceptual record occurrences using the physical/conceptual mapping, then derives the required external record occurrence from the conceptual records constructed using the relevant conceptual/external mapping. Advantages of DBMS You have seen that data independence and the consequential benefits are both an essential feature and a major advantage of database systems. Yet another essential feature is the centralization of related data. This phenomenon results in further advantages of database systems. These are:  The stored data can be shared relatively easily  New applications may be developed using the existing database  Standards for representation of data can be laid down and enforced among different installations. This can significantly reduce the maintenance activity and enhance data compatibility among installations.  With a centralized control of data, the database system may be designed for an overall optimal performance from the viewpoint of the entire organization. © SQL Star International Ltd. 8
  • 12.  Ensuring data security becomes much easier as access to the database can be controlled through establishment of proper channels and authorization checks. However, to realize the above benefits, proper organizational infrastructure is needed. The most popular way to support the Database environment is to establish the office of the Database Administrator (DBA). In fact, the DBA may be a single person or a team. He is responsible for the centralized control of the database. The Database Administrator The database administrator is responsible for the overall planning of the company‘s data resources, for the design of data, and for the day-to-day operational aspects of data management. The overall planning of corporate data is the strategic aspect of the database administration function and involves company-wide planning of existing data and assessment of organization-wise data standards. Some of the design aspects of database administration work are:  Deciding on the storage structures and access methods  Selecting database software and hardware  Designing restart and recovery procedures to take care of system outages or crashes  Designing means of reconstructing data in the event of abnormal loss of the same  Designing scheme  Designing the means of reorganizing or tuning databases periodically  Designing database searching strategies  Designing authorization checks and validation procedures  Specifying techniques for monitoring database performance The operations management of database administration deals with data problems arising on a day-to-day basis. Specifically, the responsibilities include:  Investigation of errors found in the data  Supervision of restart and recovery procedures in the event of a failure  Supervision of reorganization of databases  Initiation and control of all periodic dumps of data. © SQL Star International Ltd. 9
  • 13. In addition, this aspect of database administration includes maintenance of data security, which involves maintaining security authorization tables, conducting periodic security audits, investigating all known security breaches. To carry out all these functions, it is crucial that the DBA has all the accurate information about the company‘s data readily on hand. For this purpose he maintains a data dictionary. The data dictionary contains definitions of all data items and structures, the various schemes, the relevant authorization and validation checks and the different mapping definitions. It should also have information about the source and destination of a data item and the flow of a data item as it is used by a system. This type of information is a great help to the DBA in maintaining centralized control of data. Types of DBMS The different types of DBMS available are:  Hierarchical database management system  Network database management system  Relational database management system  Object Relational database management system Hierarchical DBMS Hierarchical DBMS (HDBMS) is one of the oldest methods used for organizing and storing data. In a hierarchical database, data is organized in a pyramid fashion, just like the branches of a tree extending downwards. In a hierarchical database you need to understand the concepts of record type and parent-child relationship. Let us take an example. In the order processing of any organization, orders are placed for different products. Orders comprise the following information, which are also called field values: • Order number • Order date © SQL Star International Ltd. 10
  • 14. Customer number • Product number Similarly, products comprise a collection of: • Product number • Product type • Product name • Quantity • Price The collections of these field values are called records and groupings of records of the same type are called record types. Related records are grouped together so that you can have higher-level records and lower-level records, similar to how the parents in a family tree sit above the subordinated children. In the example, Orders and Products are the two record types and the relationship between them is the parent-child relationship. Hierarchical Database Management System In the diagram, the parent record (Orders) at the top of the pyramid is called the root record. The parent record has three child records linked to it. The root of the hierarchical model cannot act as the child record type. Except the root, every record type acts as a child record type in exactly one parent-child relationship. The child records can have only one parent record. In contrast, a parent record may have more than one child record linked to it. Each child record can also be a parent with child records underneath it. Hierarchical DBMS works by moving from the top of the pyramid to its bottom. A record search is conducted by working down through the pyramid from parent to child until the suitable child record is found. The pyramid like structure and the defining of relationship between records in advance makes it easy to access and update hierarchical databases. © SQL Star International Ltd. 11
  • 15. However, there are few limitations with HDBMS. The relationship between child records is not permitted, even if they make a logical sense. Moreover, the hierarchical design is so rigid that adding a new record requires the redefinition of the entire database. Network DBMS Network DBMS (NDBMS) is an extension of HDBMS. Instead of having a pyramid like structure, a NDBMS looks more like a spider web or interconnected network of records. In NDBMS, child records are called members and parent records are called owners. In the network data model too, data is stored in records and descriptions of the structure of a group of records of the same type are stored in record types. Record types are linked or related using the set types. Set types consist of: • A set type name • An owner record type • A member record type Consider an example of orders and it‘s products. The two record types are Order and Product, the former being the owner record type and the latter being the member record type. They are linked using the set type ProdOrder, which represents the relationship between orders and products in them. The relationship is of 1:N meaning that there will be many set occurrences (or instances) where one record from the owner record type Order relates to a set of records from the member record type Product. That is, an order can have one or more products in it. Therefore, set occurrences are composed of: • One record from the owner record type • A number of records (zero or more) from the member record type Network Database Management System © SQL Star International Ltd. 12
  • 16. In the figure there are three set occurrences of ProdOrder set type, which are Product1, Product2, Product3. A record of the member record type cannot exist in more than one set occurrence, that is, two customers cannot buy the same product. Similar to HDBMS, NDBMS structure and relationship must be defined in advance. The number of connections that can be made between records is also limited. Relational Database The databases mentioned so far including the file system databases were not very efficient. In the file system, users cannot simultaneously access data from the same file, managing the files is very tedious when data stored is complex and accessing data from files is also very tedious. HDBMS and NDBMS does not allow many-to- many relationships, has complex path to navigate and retrieve data, and the relationship between data is in the form of pointers. The objective of developing the relational model was to overcome the shortcomings of those systems that existed at the end of the 1960s, and to make DBMS products more appealing to all kinds of users. Dr. E. F. Codd first introduced the relational model when he proposed the relational model principles in a paper called ―A Relational Model of Data for Large Shared Data Banks‖ in June 1970. A relational database stores data using relations where each relation resembles a table of values. Each row in a table contains collection of data values. For example, a university stores information about all it‘s students using tables referred to as a Student table and a Course table. Student table contains details about students, such as, their student number, name and the course code. As different data is stored in the two tables, we may need to combine them to answer particular questions such as details about students pursuing course ‗Electronics‘. An RDBMS enables to relate data in one table to the data in another. It does so by identifying the relationships, which are represented by primary key and foreign key. A primary key is assigned to that column, which will enable you to identify each row of data in a table uniquely. For example, in the Course table the column containing the course code is the primary key as it helps to identify each course uniquely. A foreign key is assigned to a column of a table, which refers to the primary key column in another table. For example, in the Student table the column containing the course code refers to CourseCode column of the Course table. © SQL Star International Ltd. 13
  • 17. Object Relational Database Hierarchical, network and relational database models have been quite successful in storing data for traditional business applications. But, object oriented databases evolved to handle more complex applications such as databases for scientific experiments, geographic information system, engineering design and manufacturing. An object oriented database stores data, their relationships and the way they interact with other data. As compared to the relational database approach, which deals with data at the lowest level, that is, columns and rows, the object oriented approach deals with data at a higher level, that is, with the objects surrounding the data. RDBMS Dr. E.F.Codd outlined the principles of the relational model, which formed the basis for the evolution of the Relational Database Management System. A Relational Database Management System is defined as a collection of tables related to each other through common values. Evolution of RDBMS Before the acceptance of Codd‘s Relational Model, database management systems was just an ad hoc collection of data designed to solve a particular type of problem, later extended to solve more basic purposes. This led to complex systems, which were difficult to understand, install, maintain and use. These database systems were plagued with the following problems:  They required large budgets and staffs of people with special skills that were in short supply.  Database administrators‘ staff and application developers required prior preparation to access these database systems.  End-user access to the data was rarely provided. © SQL Star International Ltd. 14
  • 18.  These database systems did not support the implementation of business logic as a DBMS responsibility. Hence, the objective of developing a relational model was to address each and every one of the shortcomings that plagued those systems that existed at the end of the 1960s decade, and make DBMS products more widely appealing to all kinds of users. The existing relational database management systems offer powerful, yet simple solutions for a wide variety of commercial and scientific application problems. Almost every industry uses relational systems to store, update and retrieve data for operational, transaction, as well as decision support systems. Basic Relational Database Terminology In a relational database, the entities of the ERD are represented as tables and their attributes as the columns of their respective tables in a database schema. The components of a database schema include:  Tables: Tables are the basic storage structures of a database where data about something in the real world is stored. It is also called a relation or an entity.  Rows: Rows represent collection of data required for a particular entity. In order to identify each row as unique there should be a unique identifier called the primary key, which allows no duplicate rows. For example in a library every member is unique and hence is given a membership number, which uniquely identifies each member. A row is also called a record or a tuple.  Column: Columns represent characteristics or attributes of an entity. Each attribute maps onto a column of a table. Hence, a column is also known as an attribute.  Relationship: Relationships represent a logical link between two tables. A relationship is depicted by a foreign key column. Some optional properties of relational tables include the following:  Data items (fields) must have a single value.  Data values in columns are of the same kind. This property states that all values in a given column must come from the same domain. Let us understand the concept of a domain. Suppose, you have a CourseName column in the Course table, which is defined to be a character string of length 15. The possible values this column could have are:  Oracle10g  Java  E-commerce  C++ © SQL Star International Ltd. 15
  • 19. Visual Basic Let us name this list as ‗course-names’ and define a rule that the contents of CourseName should not only be characters of length less than 15, but must also contain values that are part of ‗course-names’. Here, ‗course-names’ becomes the domain and CourseName is in the domain of ‗course-names’. Each row is unique  The sequence of columns (left to right) is insignificant. The benefit of this property is that columns can be retrieved in any order.  The sequence of rows (top to bottom) is insignificant. The benefit of this property is that rows can be retrieved in any order, that is, the third, fourth or fifth row of member details could be retrieved.  Each column must have a unique name. As mentioned above, the sequencing of columns being insignificant, columns must be referred by name and not by their position. Normalization One of the methods of designing a database is normalization of steps. What do you mean by normalization? Normalization can be defined as the technique implemented to remove redundancy from an existing set of tables. Normalization helps:  Reduce redundancy  Increase integrity  Stabilize design  Identify any missing data A relational table is normalized if it satisfies a certain set of constraints, which are that they should be free of data redundancy and that they can be modified consistently and correctly. Therefore, normalization is the process of removing redundant data by splitting a table into smaller tables. The technique of normalization includes some rules, which when applied, changes un-normalized data to a structured and normalized state. The process of normalizing is implemented in levels called normal forms. There are three such stages, they are:  First normal form  Second normal form  Third normal form © SQL Star International Ltd. 16
  • 20. First Normal Form (1NF) The first normal form can be defined as the level where the tables represent a set of two-dimensional structures and contain no repeating groups. You need to implement the following set of steps to convert your un-normalized data to its first normal form.  Identify the primary key  Remove all repeating columns  Create a new table to contain the repeating columns  Add a primary key column to the newly created table so as to ensure uniqueness  Add a foreign key column to the new table. It should be the same column at the primary key in the base table. To understand better, follow the example given. Example To arrive at a functionally efficient library database schema, you would have to normalize the tables of the library database. The main table used in the library is where the transaction details will be stored. You would require:  All information pertaining to the customers who borrow books  All information of the borrowed book, such as its author, its publisher‘s information and the dates of issue and return  The un-normalized table is as follows  © SQL Star International Ltd. 17
  • 21. © SQL Star International Ltd. 18
  • 22. This table can be brought to the 1NF by removing all the repeating columns. The repeating columns are put into separate tables in logical groups with a primary key as a unique identifier for each table. The tables in the first normal form are: Second Normal Form (2NF) The second normal form can be defined as the level where tables are in the 1NF, and where for every table, all its non-primary key columns are dependent on the whole primary key. A column should not be partially dependent on the primary key. When a column depends on part of the primary key it is called partial dependency. To remove partial dependency: 1. Identify the non-primary key columns and remove them from the tables 2. Create another table to contain the removed columns, and the primary key column that they are dependent on. To bring a table to the 2NF, any of the following rules should be met:  The primary key column should not be a composite key. That is, it should be made up of only one column.  All the non-primary key columns are dependant only on the primary key.  There should be no non-primary key dependent columns in the table. To bring the tables to 2NF, remove all those columns that are partially dependent on the whole primary key. For instance the book availability does not depend on the transaction ID but only on the book ID. So that column can be removed into a new table. Hence, the tables in the second normal form will be as follows: © SQL Star International Ltd. 19
  • 23. Third Normal Form (3NF) The third normal form is defined as the level where the non-primary key columns in the tables are directly dependent on the primary key and are not dependent on any other non- primary key. If you remove the transitive dependencies from a table in 2NF, then it is said that, “the non-primary key columns are dependent on the primary key, the whole key and nothing but the key”. Steps to convert a table to the third normal form are: 1. Identify the non-primary key columns that depend on other non- primary key columns. 2. Remove the columns arrived at in the first step from the base table. 3. Create another table with the removed columns and include the non-primary key column that they are dependent on making it the primary key. 4. Create a foreign key in the base table linking it to the primary key in the new table. © SQL Star International Ltd. 20
  • 24. To bring the tables to their third normal form remove the non-primary keys that are dependent on other non-primary keys and also remove the columns that are calculated or derived columns. The membership fee a non-key column depends on the age of a member, which is another non-key column. Tables in the third normal form are: The Entity Relationship Model The conceptual level model is a very important model in typical database architecture. To represent or model data at this level, three major data models namely, network, hierarchical and relational, have been proposed which you shall examine later. Each of these models has its own pros and cons. The entity relationship model is not a formal data model, unlike the three mentioned above. However, this model is a more natural view of the real world, which consists of entities and relationships, as you shall see shortly. Therefore, this model is very useful for understanding the concept of data modeling. The three formal models employ certain ways of representing data known as data structures; essentially to represent the ―entity relationships‖ existing in the real world. The entity relationship model (E-R model) clarifies concepts regarding what entity relationships are, and what modeling entity relationships existing in the real world means. Therefore, a study of the E-R model should be an appropriate first step towards understanding the three major data models. © SQL Star International Ltd. 21
  • 25. Entities An entity is a thing, which can be distinctly identified. What is important over here is that it is individually distinct. Employees, a house, a supplier to an organization, are all entities. Identification of entities relevant to a database is extremely important, because, a database contains data about entities. All entities of the same type form an entity set. ―All Employees‖ form an entity set and so do ‗All Suppliers‘. Distinguishing Entities As has been stated, an entity is a distinctly identifiable thing. To distinguish one entity or one member of an entity set from another, one needs some means of distinction. This distinction is achieved through values of what is known as the ―Key Attribute‖ of the entity. The database gives information about different entities contained in it. This information is about different properties of each entity. For example, a personal database contains information about employees (here employee is the entity). The properties of an employee about which information is given, may typically be, employee number, name, date of birth, date of joining the organization, total job experience and educational qualifications. Each of these properties is called an attribute of the entity. Each of the attributes can take on a value from a range of possible values, which is known as the domain of values for that attribute. The values need not be only numerical but may also be character strings. For each entity in an entity set, there is an attribute, which distinguishes the entity uniquely from the other members of the set. This attribute is the key attribute for the entity-set. For example, the employee entity-set discussed about can have either the employee number or the employee name (assuming no two names are identical) as the key attribute. In some cases, a combination of more than one attribute may act as a key, instead of just one key attribute. Some times, an arbitrary serial number may have to be supplied as the key attribute. There are special cases where the members of an entity-set can be distinguished from one another only by their relationship to entities of another type. The ‗is a‘ relationship is one such relationship. These cases will be illustrated when we take up an actual example of an E-R model later. Relationships In a real-world situation, certain entities are associated with each other. For example, referring to the employee entity-set will have a relationship with the department entity-set signifying the department for which an employee works. This relationship can be expressed as the ―works-for‖ relationship from ―employee‖ to ―department‖. A relationship may exist amongst the members of the same entity-set. For example, in the employee entity-set, some employees may be seniors of certain other employees. Therefore a relationship ―senior-of‖ may exist between one member of the employee entity-set and a few other members of the same set. © SQL Star International Ltd. 22
  • 26. A diagrammatic representation for the employee-department relationship may be as given below. A diagrammatic representation for the ―senior-of‖ relationship may be: It should be noted that relationships convey very important information regarding the relevant real world situation just as entities do, and hence should be properly represented. There may also be relationships involving more than two entity sets. For example, Prof. Smith teaching Economics to a student named Sam. This relationship contains two relationships – (1) Prof. Smith teaches Economics and (2) Prof. Smith teaches Sam. These two relationships cannot be combined to deduce the information given by the original relationship. The same entity-sets may be also linked by more than one relationship. For example, the Professors and the Students entity-sets may be linked by the two relationships, viz; (1) TEACHES and (2) ADVISOR-O Types of Relationship Relationships between the entity-sets can be classified according to how many members of one entity-sets are related to one member of the other entity-set and vice-versa. Accordingly, the following types of relationships can be identified. One-to-One Relationships If a one-to-one relationship exists between two entity-sets A and B, it means that with each entity in A, at most one entity in B is associated and vice-versa. Strict one-to-one relationships are not very common in real world situations. Consider an entity set of traffic policemen and another entity-set of traffic control points in the city and assume that only one policeman controls one traffic control point. Under this assumption, the relationship CONTROLS between the entity sets POLICEMEN and CONTROL-SITES will be a one-to-one relationship. Many-to-one Relationships This type of relationship is quite common in everyday life. If, with each entity in the entity-set B, zero or more entities in set A are associated, then we say that a © SQL Star International Ltd. 23
  • 27. many-to-one relationship exists from set A to set B. In our earlier employee database example, the WORKS-FOR relationship is a many-to-one relationship from the entity-set EMPLOYEES to the entity-set DEPARTMENTS (assuming that an employee works for only one department at a time). Many-to-Many Relationships This is yet another type of relationship which is quite common in real-life situations. In this case, associated with each entity in set A, there may be zero or more entities in set B and vice-versa. A very common example of this type would be the relationship between the entity-set SUPPLIERS and the entity-set PARTS. A supplier may supply many parts, while a part may be supplied by many suppliers. Guidelines for Constructing the Entity-Relationship Model Having understood the basic components, you are now in a position to consider the construction of an E-R model. The principal steps involved in this exercise are: • Select relevant entity-sets for the real-life situation under consideration • Select relevant attributes for each entity-set • Identify the key-attribute for each entity-set • Determine the type of each of the relationships between the entity sets • Draw the E-R diagram Consider the situation in which the academic administration often finds itself. It has to handle data regarding students, faculty, and the courses being offered, and possible areas of specialization. It is worthwhile to consider the following points before you move to construct the model: • The students specialize in one or more areas • The students study a specific course • A course belongs to an area of specialization • A faculty member belongs to an area of specialization • A student can be either a doctoral student or a degree student • A faculty member guides a doctoral student • Certain courses have certain other courses as prerequisite • A faculty member offers a specific course From the above, the desirable entity-sets, their relevant attributes and the appropriate key attributes can be determined. 1. Entity-set : Students Attributes : Roll No, Name, Date-of-birth, Basic Educational Qualification, No. of years of work experience © SQL Star International Ltd. 24
  • 28. Key : Roll No. 2. Entity-set : Faculty-members Attributes : Name, Date-of-birth, Date of Joining, Educational Qualifications, Total No. of years of Teaching Experience Key : Name 3. Entity-set : Courses Attributes : Course-No, Course-Name Key : Course-No 4. Entity-Set : Areas (of specialization) Attributes : Name of the Area Key : Name of the Area 5. Entity-Set : Doctoral-students Attributes : None This entity-set is needed to identify individual doctoral students. The reason for assigning a separate entity-set to doctoral students is to be able to establish the relationship between these students and their faculty guides, in the actual database. Now you are in a position to identify the different relationships amongst the above entities. These are: 1. SPECIALISES_IN: This is a many-to-many relationship between STUDENTS and AREAS 2. STUDIES: This is a many-to-many relationship between STUDENTS and COURSES 3. INCLUDED_IN: This is a many-to-one relationship from COURSES to AREAS 4. BELONGS_TO: This is a many-to-one relationship from FACULTIES to AREAS 5. GUIDES: This is a one-to-many relationship from FACULTIES to DOCTORAL- STUDENTS 6. OFFERS: This is a many-to-many relationship from FACULTIES to COURSES. The assumption here is that a course may be offered by more than one faculty-member 7. IS A: This relationship is one-to-one between STUDENTS & DOCTORAL-STUDENTS 8. PREREQUISITE_FOR: This is a many-to-many relationship from COURSES to COURSES because a course may be a prerequisite for more than one other course and may have more than one other course as prerequisites for itself Now you are ready to draw the E-R diagram representing the E-R model. First let us discuss the relevant diagrammatic conventions and then actually draw the diagram © SQL Star International Ltd. 25
  • 29. Conventions for Drawing E-R Diagrams Following are the conventions for drawing E-R diagrams: · Entity-sets are represented by rectangles. · Attributes are represented by circles. These are linked to the appropriate entity-sets by undirected edges. · Relationships are represented by diamond shaped boxes. These are linked to the appropriate entity-sets by directed edges. An E-R diagram for the Academic Administration database is: As already stated earlier, the E-R model brings out the essential features of data modeling for databases. Data modeling in practice, is done according to the one of the three models, viz., hierarchical, network and relational. The three models too, establish relevant entities and the relationships amongst them; they differ in the way they represent data about both entities and their relationships. The E-R model, however, is free from these relatively physical aspects of data representation and therefore can be said to be a general view of the three models unifying them at a relatively abstract level. Case Study – Entity Relationship for a Library The library needs to create a database to automate its data storage and processes. For this you first need to know how a library functions, what are its transactions and what data it needs to store for activities. To arrive at an ERD for a library, list the entities and its attributes you require before putting them into a diagram:  Member  Member ID  Name © SQL Star International Ltd. 26
  • 30. Address  Area  Zipcode  phone number  Age  Date of membership  Age group  Branch ID  Book  Book ID  Book name  Author name  Publisher  Published Year  Category  Branch  No of copies in store  Transaction  Transaction ID  Member ID  Book ID  Issue date  Return date  The actual return date  Fine to be paid by the member for default  Category (for books)  Category ID © SQL Star International Ltd. 27
  • 31. Category description  MemberFee  Age group grade  Minimum value  Maximum value  Fee amount  Branch  Branch ID  Branch name  Address  Location  Phone number  Date of establishment  Availability  Book id  Available copies  Publisher  Publisher Id  Name  Address The list arrived at above can be depicted as an ERD in the following manner: © SQL Star International Ltd. 28
  • 32. Communicating with RDBMS In order to communicate with the RDBMS, that is, to access data, you have a query language called a Structured Query Language (SQL). A query can be defined as a request made to access data from the database. This definition refers not only to data retrieval, but also defining, manipulating and controlling data. The need to access data from the database on an ad-hoc basis led to the origin of SQL. The origin of SQL can also be associated with one of Codd‘s Twelve Rules, where in he states that a relational database must have a high level language capable of handling all communication with the database. Although there are several languages that can access data from the database, SQL is the primary language for communicating with RDBMS. SQL can also operate on non-relational databases. © SQL Star International Ltd. 29
  • 33. Features of SQL The features of SQL are as follows: • SQL is a Declarative Language (non-procedural). You need not provide the Step wise procedure to be followed in order to access the data. Instead, it allows you to simply declare what data you want without having to provide details about where it is located or how to get it. It leaves it to the DBMS to determine the best way to get it. On the contrary, procedural languages such as C, or C++ provide a step-wise procedure telling the computer exactly what is to be done. The advantage being that these instructions given ahead of time can be compiled into machine language for fast execution. But these languages lack flexibility, that is, do not adapt to changes easily. • SQL is a set-based language. Since the relational model uses the concept of a mathematical relation that is, has its theoretical basis in set theory, SQL supports set operations and relational algebra operations. A set is an unordered collection of elements of the same type and structure. Tables (or relations) are called sets and rows (or records) are their elements. In a relational database the physical positioning of rows is not important, that is, they are unordered, so SQL being a set-based language can operate on an entire table, or multiple tables at once. In contrast, a procedural language can operate on a single record at a time as it uses ‗files‘ which are similar to tables, wherein records have a physical ordering. Relational algebra operations can be divided into two groups:  Set operations from mathematical set theories including Union, Intersection and Set Difference.  Operations developed for relational databases, which include Select, Project and Join. Set Operations Set operations include the following:  Union  Intersection © SQL Star International Ltd. 30
  • 34.  Set Difference Union To understand the union operation look at the following two tables, States1 and States2: The above two tables contain names of US states. Some of the state names are common in both the tables. In order to return the state names that are in States1 or in States2 or in both States1 and States2, eliminating duplicate rows, you use the UNION operation. The notation for union of tables is: States1 UNION States2 = States3 The result of the union operation is as follows: States 3 Hawaii New Jersey Indiana Florida Arizona Colorado California Alaska Texas Georgia Virginia Wisconsin Kansas Kentucky Iowa The resulting table contains the state names that are contained in both the tables, but displaying the common state names only once. © SQL Star International Ltd. 31
  • 35. Intersection The intersection operation returns state names that are in both States1 and States2, that is, it returns a third table that contains only common state names. The notation for intersection of tables is: States1 INTERSECTION States2 = States3 The result of the intersection operation is as follows: Set Difference The result of the set difference operation returns state names that occur in the States1 table but not in the States2 table, or also vice versa. The result is as follows: Relational Operations In addition to set operations, certain other operations were developed for relational databases, which include:  Selection  Projection  Joins Selection The selection operation enables you to retrieve only specific rows that match your criteria. For example, you have two tables TabA and TabB. © SQL Star International Ltd. 32
  • 36. Using the selection capability of SQL, you can retrieve those rows from TabB table where Col1 value is 2. The result set of rows would be: Projection The projection operation enables you to retrieve only specific columns from the total columns available. For instance, using the projection capability of SQL, you can retrieve only Col2 values from TabA table. The result set would be: Joins The join operation enables you to retrieve data from more than one table. For instance, using the joining capability of SQL, retrieve rows from both TabA and TabB by joining Col1 as they have equivalent values. The result set of joining the two tables would be: Why SQL is Preferred? SQL is favored due to the following reasons: © SQL Star International Ltd. 33
  • 37.  A wide range of users, including those with little or no programming knowledge can use it.  It is an English-like language.  It is non procedural, that is, the user need not specify the method to be followed to arrive at the result, rather just specify the result that needs to be arrived at.  It allows defining, retrieving and manipulating data in the tables. Relational Data Model Concept This rule states that all data is represented as tables. Data can be viewed in no other way. Codd’s Rules Dr. E. F. Codd, was the creator of the relational data model. It was published as a two- part article in ComputerWorld (Codd, 1985). It contains a list of 12 rules that determine whether a DBMS is relational and to what extent it is relational. These rules are a very useful yardstick for evaluating a relational system. In the article, Codd mentions that according to these rules, there is no database yet that is fully a relational system. He says that rules 6, 9, 10, 11 and 12 are difficult to satisfy. Each of the twelve rules is briefly discussed below. The Information Rule All information in a relational database is represented explicitly at the logical level and in exactly one way through values in tables. Guaranteed Access Rule Each data item must be accessible by providing table name + primary key of the row + column name. © SQL Star International Ltd. 34
  • 38. Systematic Treatment of Null Values Handle missing or non-applicable data, that is, nulls, in a consistent manner. Nulls should have no values and should simply be missing data. Treating Null as a zero for missing numeric data or as a blank for missing character data violates this rule. Vendors provide the ability to use default values for missing data, if so desired. Self-describing Database In addition to storing user data, a relational database must contain data about itself. There are two types of tables in RDBMS: user tables, which contain data required by users, and system tables, which contain data about the database structure. The data that describes the database structure is called meta-data. The collection of system tables is called as the system catalog or data dictionary. Storing any part of the data dictionary in operating system files would violate this rule. Comprehensive Data Sublanguage The data access language (SQL) must be the only means of accessing data stored in the database. The language must support relational operations and set operations with regard to the following:  Data definition  Data manipulation  Integrity definition  Transaction control  Data control Accessing data files (files that contain the actual data), through a utility other than an SQL interface, violates this rule. View Updating Rule There are situations where users may require only a part of the table information or information from a collection of tables. Such requirements can be met by creating ‗Views‘. Views are virtual tables, which unlike a table contains no data, just statements that return data in the form of tables. This rule states that views should allow updates in the underlying tables and vice versa. But SQL supports only updates of single tables at a time (see rule 7), therefore if, you join three tables to create a view, and try to update that view, then DBMS would fail to translate these updates to the underlying tables, thereby violating this rule. Also, a view not including the column that uniquely identifies each record in a table cannot be updated, thus violating the rule. This rule will be dealt in depth in the chapter on ―Views‖. High-level Insert, Update and Delete This rule states that in a relational database, the query language (SQL) must be capable of performing manipulations (such as, inserting, updating or deleting data) © SQL Star International Ltd. 35
  • 39. on sets of rows in a table. A database that supports only row-at-a-time manipulation cannot be considered as relational. Physical Data Independence This rule states that in a relational database, any changes made in the way data is physically stored (that is, data stored in file systems specific to the machines operating system) must not affect applications that access data. If a file supporting a table was moved from one disk to another or renamed, then this should have no impact on the application. Logical Data Independence This rule states that changes to the database design should be done in a way without the users being aware of it. The change could be to expand the database (adding a new table) or to reduce it, but the application that refers to the data (logical) must work as before. If a single table were split into two, then a view would have to be provided joining the two back together so that there would be no impact on the application. Integrity Independence In order to be considered as a relational database, all data integrity, which are definable in the query language referred to in rule 5 must be stored in the database as data in tables, that is, in the catalog and not in the application programs. The data integrity rules that should apply to relational databases are: Entity integrity- the primary key column cannot have missing values Referential integrity- for every foreign key column value there must exist a matching primary key column value. Integrity rules are covered in depth in a later chapter. Distribution Independence In a relational database, data can be stored centrally (on a single system) or distributed (across a network of systems). The data in a centralized database should remain logically unaffected if they are distributed across systems. For example, a user should be able to retrieve data from two tables distributed across two terminals, the same way, as they would retrieve them if stored in the same terminal. Non-subversion Rule This rule states that there should be no other access path to the database, other than SQL. Any other access language may bypass (or subvert) security or integrity rules, which otherwise would be obeyed by the regular data access language. © SQL Star International Ltd. 36
  • 40. Summary In this chapter, you have learnt that: Files prove to be inefficient due to their redundant nature when the number of applications increase. This gave rise to the concept of Database. Database is a collection of logically related data stored on media. To handle and maintain this database, a software, Database Management System (DBMS) came into existence. They are of 4 types: 1. Hierarchical Database Management System 2. Network Database Management System 3. Relational Database Management System 4. Object Relational Database Management System  Out of these types, Relational Database Management System (RDBMS) was popularly used which enables to relate data in one table to the data in another. Normalization is the process to stabilize a database, by reducing data redundancy. Data can be stabilized through 3 stages: 1. First Normal Form (1NF)   2. Second Normal Form (2NF) 3. Third Normal Form (3NF) To access the stabilized data, Structured Query Language (SQL) is widely used. © SQL Star International Ltd. 37
  • 41. Lab Exercise In the following questions, you are given the Universe of Discourse (UOD, that is, the general outline at the level a user would normally describe) of some typical enterprises. Please note that a UOD is not a smooth and structured description. Define:  Entity and associated attributes  Relationships between entities and type of relations  Draw the Entity-Relationship diagram 1. LIBRARY SYSTEM: A library keeps records of current loans of books to borrowers. Each borrower is identified by a borrower number and each copy of a book by an accession number. The name and address of each borrower is held so that overdue loan reminders etc., can be sent whenever necessary. The information required about books is the title, authors, publishers, publication date, International Standard Book Number (ISBN), purchase and price and current price. There is a restriction on the number of books a borrower may have on loan at any one time, the limit depending on whether a borrower is classified as having junior or adult status. Books out on loan may be reserved by other borrowers pending their return. The library stocks only the hardback version of the book. If a new edition of the book is published, all copies of earlier editions are withdrawn from stock. 2. A UNIVERSITY: A University has number of departments. Each department has its faculty. Departments enroll students. Each faculty member may conduct one or more courses and one or more students register for a course. The courses are conducted in classrooms based on a prepared time-table. Each subject has a prescribed text book and host of recommended reference books. A faculty member may guide more than one project and the same project may be done by more than one student. 3. DEPARTMENTAL STORE: The data in the database of a department store are defined as follows:  Each employee is represented. The data about an employee are his employee number, name, address and the department he works for.  Each department is represented. The data about departments are its employees, manager and items sold.  Each item sold is represented. The data about items are its name, manufacturer, price, model number (assigned by the manufacturer) and an internal item number (assigned by the store). © SQL Star International Ltd. 38
  • 42.  Each manufacturer is represented. The data about a manufacturer are its name, address, items supplied to the store and their prices. Various employees work for a department and each department stores items supplied by various manufacturers. A MANUFACTURING ENTERPRISE: A manufacturing company consists of a number of divisions. Each division, in turn, consists of one or more departments. Each employee of the company belongs to only one department at any point of time. Orders are executed at the divisional level. Any number of departments (as required) may execute an order. A department may also execute a number of orders. Employees work on various orders in the organization. An order needs several parts. A part may be needed by several orders. A part itself may consist of sub parts. Alternatively, a part may be a support of a super part. Parts are housed in warehouses which are at specific locations. Suppliers supply parts. AN AIRLINES ENTERPRISE: An Airlines company has a fleet of aircraft‘s which it employs to carry passengers from one airport to another. A flight (i.e. an aircraft assigned for trip from one airport to another) is manned by a crew. A time table is available for all the flights. At each airport, based on the flight schedules, service schedules are drawn up for the ground staff. At each airport, for each flight, caterer(s) provide the necessary food and refreshments according to the catering schedule. The maintenance of aircraft‘s (that are not in operation and which have been tagged for maintenance) is done by the maintenance staff according to the maintenance schedule. Maintenance is conducted at the airports where hangar(s) are available for the type of aircraft in question. © SQL Star International Ltd. 39
  • 43. Chapter 2 Introduction to Oracle10g Key features of Oracle10g Components of Oracle10g © SQL Star International Ltd. 40
  • 44. Objectives At the end of the chapter, you will be able to:  Identify the different components of Oracle10g  Identify the enhanced features of Oracle10g © SQL Star International Ltd. 41
  • 45. Introduction The traditional database systems such as relational, hierarchical and network have been successful in developing the database for traditional business applications such as banking and railway reservations. But, when it comes to more complex business applications such as databases for scientific work, engineering designs, telecommunications, geographic information system and multimedia, the traditional database systems cannot handle them because the requirements and characteristics of these applications are different from the traditional business applications. These applications require more complex structures for:  Storing data related to real world objects such as engineering diagrams, molecular structures, or financial instruments  Transactions, which would be for longer durations  New data types required for storing complex multimedia data such as audio and video clips, images and maps. Oracle10g Database meets the above needs as it tightly incorporates ORDBMs concepts. Object Relational Database Management System (ORDBMS) is a database management system that has evolved from the relational model and includes both the relational and object-oriented technology. Oracle8.0 was the first version of the Oracle database to incorporate object-oriented technology. In Oracle10g, ‗g‘ stands for GRID. This release is focused on efficient management of infrastructure based on its grid computing mechanism. Now, the question arises what is Grid Computing? The idea behind the grid computing is to utilize the resources available, to the maximum extent by dynamically pooling it based on the requirement of the end user during the peak hours. In this case, the end user need not know the whereabouts of the resource. Infrastructure Advantages Data Availability Internet database availability is critical for any eBusiness application. Oracle10g focuses on the following areas to achieve continuous data availability:  Zero data loss data protection environment  Support for online reorganization and redefinition architecture to reduce offline maintenance requirements  Provides more complete and precise database repair capabilities by ensuring better prevention and improved handling of disk corruption © SQL Star International Ltd. 42
  • 46. Scalability and Performance Oracle10g enables eBusiness to scale millions of users performing millions of transactions per hour by focusing on the following key areas:  Transparent cluster scalability and performance: Oracle10g along with its grid mechanism includes Real Application Clusters (RAC) that has been designed to provide continuous data availability while increasing the scalability and performance of the database infrastructure. RAC was introduced in Oracle9i, which is an arrangement, where a single database runs on a group of servers that are clustered together. With Oracle9i RAC all servers in the cluster act as backup to each other while at the same time increasing the overall computing power within the cluster.  Scalable session state management: Oracle10g allows more users to be hosted on the same or larger hardware platforms due to its new grid mechanism where in new nodes can be added to the cluster when the load increased.  Optimized features critical for eBusiness: Oracle10g focuses on the following performance areas, critical for eBusiness: Support for large datafiles. Enterprises planning to setup Data Warehouse and transaction systems can extend their Oracle database upto 8 Exabytes, which is equivalent to 8 million terabytes.  Improving the performance of many of today‘s business applications by providing support for enhanced native compilation and improved optimization of PL/SQL.  Improving optimization plans and reducing resource usage by adding memory and CPU costs to the cost based optimizer cost calculation algorithm  Improving performance in Data Warehouse and Online Transaction Processing (OLTP) environments by general I/O improvements such as better sharing of run-time data structures, larger buffer caches and deferrable constraints. Security Oracle10g provides secure application development and deployment platform by focusing on: A strong three-tier security, which ensures that a user can access the database only through the middle tier. As a result user identities are maintained securely through all tiers of an application, with centralized user and privilege management in Oracle Internet Directory. Deep data protection through enhancements in Virtual Private Database, fine-grained auditing and Oracle Label Security Development Platform for eBusiness Applications Oracle10g continues to provide the best development platform for both eBusiness and traditional application development by focusing on the following key area © SQL Star International Ltd. 43
  • 47. Enterprise Java Engine: Java support in Oracle10g focuses on improving the performance of the embedded Java Virtual Machine, new JDBC and SQLJ functionalities, and enhancement to Java stored procedures.  SQL and PL/SQL improvements: Oracle10g has introduced many enhancements in SQL and PL/SQL to meet modern development requirements. Oracle10g supports inheritance, type evolution, and dynamic method dispatch to increase the usefulness of objects. Along with the existing datatypes, new datatypes have been introduced. It also supports CASE statement, ANSI compliant joins and reserved naming conventions.  New Dataypes In addition to the existing datatypes, new datatypes have been introduced. They are BINARY FLOAT and BINARY DOUBLE. Bioinformatics and life science applications have benefited from these datatypes to solve complex computations.  Alternative Quote operator: Strings containing single code as literal, can be now be escaped using customized symbols using Q operator.  Environmental Scripts after each CONNECT: Previously glogin.sql and login.sql scripts were read at the startup of iSQL*Plus. Now, these scripts are automatically run after each user connects to the database.  Multiple Pages Output: Output spanning over multiple pages can now be viewed using NEXT button or can be viewed on a single page as in the previous version. SQLPlus Recycle Bin: SHOW RECYCLEBIN [original_name] command has been introduced to view the dropped database objects. Oracle Flashback Feature: This feature has helped a developer to reduce errors.  Oracle Flashback Table: FLASHBACK TABLE statement in SQL allows to recover the accidentally dropped table.  PURGE TABLE: This statement removes the database objects permanently from the Recycle Bin. © SQL Star International Ltd. 44
  • 48. Oracle Flashback Version Query Changes in the table data can be viewed using VERSION BETWEEN clause. A changed transaction‟s undo records stored in the database must be available. Oracle Flashback Transaction Query Changes made to the tables can be viewed using FLASHBACK_TRANSACTION_QUERY view. This can be helpful for auditing, debugging and even performance analysis. Improved MERGE Functionality MERGE Statement has been improved by making WHEN MATCHED and WHEN NOT MATCHED clauses optional. Also, WHERE clause can now be used in this statement to restrict the values while inserting into target table.  Regular Expression functions: Regular Expression functions have been introduced which works beyond the POSIX (Portable Operating System For UNIX) standard for matching ASCII characters. Improvements to PL/SQL:  Bulk Binding Enhancements: Performance related to BULK BINDING has been enhanced by introducing INDICES OF and VALUES OF clauses. INDICES OF clause permits sparse data in a collection. VALUES OF clause refers one array values based on another array values.  Enhanced Native Compilation: The number of parameters to be set for Native Compilation has been reduced. A much more tight integration of SQL and PL/SQL runtime engines is made possible.  New Packages: DBMS_WARNING: Warnings generated during compile time can be dynamically set using DBMS_WARNING package. UTL_MAIL: This is an enhancement to UTL_SMTP package. Using this, E- mails can be sent through a PL/SQL API. UTL_COMPRESS: This package compresses and uncompressed RAW Byte stream of Large Object (LOB) data. DBMS_METADATA: This package extracts the metadata of a database object, which can be obtained either in XML version or DDL. © SQL Star International Ltd. 45
  • 49. CLOB and NCLOB Implicit Conversions: You no longer need APIs to convert CLOB to NCLOB and vice versa. This release supports their implicit conversion. Oracle10g and the Internet Oracle8i was the first internet-based database in the world. It recognized that Internet provided the safest and efficient access to data to all users spread across the globe. Oracle10g continues the Oracle9i focus on the Internet by providing a series of enhancements targeted at eBusiness environments. To be able to allow commerce on the net, your system needs some important hardware configuration so that it can support the transactions between the database and the Internet. One important step is to identify the kind of machines that you need. Fat client or Thin client There are two kinds of client available, fat client and a thin client. Before debating whether everybody needs a fat client or a thin client, you need to understand what these terms mean. A fat client is a traditional PC system, which if purchased today would have 64MB or more of memory, 6GB or more of disk space, a fast paced processor and/or a CD- ROM drive. A fat client would have all the codes locally within them. A thin client is a personal computer used mainly for functions like e-mail, presentation of information and word processing. It stores no code/programs locally and only accesses them from the database. The reasons for shift from fat clients to thin clients are due to the following limitations:  Loss of critical pieces of information if they reside only on a disk drive in the event of a break down  The need for upgrading the software every time a new version comes into the market. This raises a lot of questions. Should the release of new versions force the end users to upgrade their software? Whether to assume that end- users have the necessary skills to upgrade their software? Should the support people go out to hundreds of PCs and upgrade them individually? Isn‘t this a waste of their time when these activities are only for someone who uses e-mail? The above complexities of fat client led to the development of a more mature network known as the Network Computing Architecture (NCA) wherein the end user would not be required to deal with issues like loss of data due to virus attacks or deal © SQL Star International Ltd. 46
  • 50. with upgradations. Trained professionals would handle these at some central location. Oracle Internet Platform The positioning of Oracle as an Internet solution company is due to the adoption of NCA. This architecture enables the development, deployment and integration of applications within a networked computing environment. Oracle has developed NCA, which is based on the following three separate tiers:  A thin client tier, which is the layer responsible for the presentation of the information. It is the desktop PC running a web browser.   An application server tier (the middle tier), which is the layer wherein all the application codes are processed.   A database server tier, which is the layer where all the data is stored. A Three-tier Architecture The NCA is designed such that the presentation layer is separated from the application layer. The application layer resides on a server separate from the database server and it is assumed that the application server is the fat client. The application server as well as the database server can be moved to a machine with more resources, which could be placed in a central location and be managed by trained professionals thereby keeping the end users away from all the complexities. Based on the above theoretical concepts, Oracle 10g release is broadly divided into: • Oracle Database 10g • Oracle Application Server 10g © SQL Star International Ltd. 47
  • 51. • Oracle Enterprise Manager 10g Grid Control • Oracle Database 10g Oracle10g database supports Grid Computing architecture. Here, multiple database servers are pooled together to form a cluster. It enhances utilization of resources. It efficiently stores and manages the structured and unstructured data such as: • Spreadsheets • Word documents • PowerPoint presentations • XML • Multimedia data types like MP3, graphics, video and more. Oracle 10g facilitates two-tiered or multi-layered distributed database environments like client/server and Web-based applications. Large objects need be stored inside and outside the database. Oracle Database 10g has services which help to manage and retrieve data, located outside the database. • Oracle Application Server 10g A complete infrastructural platform is provided for developing and deploying enterprise applications, integrating many functions including a J2EE and Web services run-time environment, an enterprise portal, an enterprise integration broker, business intelligence, Web caching, and identity management services. The existing 9iAS gets further enhanced with the introduction of new grid computing features. It further integrates users, applications and data across your organization. • Oracle Enterprise Manager 10g Grid Control It is the consolidated, core management console that forms the basic framework to automatically initiate administrative tasks across the networked environment. With Oracle Grid Control, multiple hardware nodes, databases, application servers and other targets can be brought together into single logical entities. Oracle10g continues Oracle Corporation’s lead on providing the best platform support for business intelligence by focusing on the challenges raised by large volume of data and the need for real time complex analysis in an eBusiness environment. Oracle10g provides the business intelligence platform by enhancing and extending database support for Online Analytical Processing (OLAP), data mining and extraction. © SQL Star International Ltd. 48
  • 52. Summary In this chapter, you have learnt that:  In Oracle10g, ‗g‘ stands for GRID. It is a technology, which groups similar resources into a cluster. This allows efficient utilization of resources. This helps us to design complex business applications.  Data availability, security and development for e-business applications are some of the advantages with Oracle10g.  Oracle10g structure is based on NCA (Networked Computing Architecture), which is developed to overcome the problems with fat client. It enables development of applications within networked computing environment.  Oracle10g has come up with new features in SQL* Plus environment, new commands in SQL language and improvements in PL/SQL, making it more user friendly. © SQL Star International Ltd. 49
  • 53. Chapter 3 Data Retrieval iSQL*Plus Interface Logging into Database using iSQL*Plus Projection, Selection and Join Terminology Differences Between SQL and iSQL*Plus Review of Syntaxes for Basic SQL SELECT statements Arithmetic and Concatenation Operators in SQL statements Alternative Quote Operator Saving SQL Statements to Script Files © SQL Star International Ltd. 50
  • 54. Objectives At the end of this chapter, you will be able to:  Use the SELECT statement to extract data   Understand the various categories of SQL statements © SQL Star International Ltd. 51
  • 55. Retrieving Data Oracle uses the Structured Query Language (SQL) to communicate with the database. The SQL statement used to extract data from the database is the SELECT statement. The SELECT statement informs the database about the data you want to retrieve. SQL statements need to be executed in an environment where, they would be interpreted and sent to database. iSQL*Plus Environment iSQL*Plus introduced in Oracle9i is a browser environment in which SQL statements are executed. SQL*Plus environment was the default environment in the prior releases of Oracle. SQL*Plus is still available. Since the Oracle server understands only SQL worded statements, all Oracle tools support SQL syntax. Implementation of SQL through SQL*Plus environment or iSQL*Plus environment meets the ANSI (American National Standard Institute) and ISO (International Standards Organization) standards. On issuing an SQL statement, the statement first gets stored in a part of the memory, which is called the SQL buffer. The SQL statements (stored in the buffer) are then recognized and submitted to the Oracle database for execution by the SQL*Plus or the iSQL*Plus environment. The iSQL*Plus environment helps to perform the following tasks:  Executing SQL statements to extract, add, change and remove data from the database  Formatting and performing calculations on query results so as to produce more meaningful reports  Storing SQL statements in files (called script files) so that they could be used later. These files have .sql file extension. How to log in to SQL*Plus and iSQL*Plus? The steps involved in logging into SQL*Plus and iSQL*Plus environments are different. Logging in to SQL*Plus Environment Logging in to SQL*Plus environment depends on the type of operating system you are working on. © SQL Star International Ltd. 52
  • 56. Logging in through a Windows environment: 1.Click Start-> Programs-> Oracle – OraDb10g_home1 2. Select Application Development -> SQL Plus © SQL Star International Ltd. 53
  • 57. 3. Enter username, password and the connect string. Logging in through a command-line environment:  Log on to the DOS prompt Enter SQL*Plus command as follows: sqlplus [username[/password[@ ConnectString]]] Where,username is the database username assigned to each user. password is the password the user enters to gain access to the database. The password is visible on entering it at the command line. Therefore, to ensure the integrity of the password, do not enter it at the command line. Instead enter it at the password prompt. @ ConnectString is the alias through which the user has to access the database. Logging in to iSQL*Plus Environment The steps to log in to iSQL*Plus environment are as follows: 1. Initiate the browser and enter the URL address of the iSQL*Plus environment. iSQL*Plus browser window is displayed. © SQL Star International Ltd. 54
  • 58. 2. Enter the username and password as shown in the following screen. Click the Login button. © SQL Star International Ltd. 55
  • 59. After you log in to iSQL*Plus, you see the iSQL*Plus window as follows: Within the windows browser, the key areas of the iSQL*Plus window are the: Enter Statements field: The area to enter the SQL statements and iSQL*Plus commands. Execute button: Click to execute the statements entered in the Enter Statements field.  Load Script button: Click to access the area for entering the name and location of a file (containing the contents of the Enter Statements field, which has been saved) or the URL for the script you want to execute. Save Script button: Click to save the contents of the Enter Statements field to a file. It is suggested that you save these files with .sql extension. Cancel Button: Click to Cancel the query presently entered by the user. A confirmation is displayed at the end. Clear Screen button: Click to clear text from the Enter Statement field, output and stops any script running at that time. Help icon: Click to access iSQL*Plus help documentation. © SQL Star International Ltd. 56
  • 60. iSQL*Plus Commands iSQL*Plus has a set of commands, which are different from the SQL statements. These commands need to be entered one line at a time. In order to continue a command on the next line, end the current line with a hyphen (-). iSQL*PLUS commands can be abbreviated. For instance, a command CLEAR BUFFER could be written as CL BUFF. iSQL*Plus commands are not stored in the SQL buffer. The main categories into which iSQL*Plus commands have been divided are:  Environment – It affects the behavior of SQL statements for the session.  Formatting – It formats the query output.  File manipulation – It saves SQL statements into script files and, loads and runs them whenever needed.  Execution – It sends SQL statements from the browser to the Oracle server.  Editing – It modifies SQL statements in the Edit window.  Interaction – It allows you to pass values into the SQL statements and also print messages to the screen. SQL Vs iSQL*Plus SQL is the language used to communicate with the Oracle server from any tool or application. iSQL*Plus is the Oracle tool, which recognizes and submits the SQL statements to the Oracle server for execution, and based on the query result, it produces formatted reports using its own commands. The following diagram depicts the SQL and iSQL*Plus interaction: © SQL Star International Ltd. 57
  • 61. Browser SQL Statements iSQL*Plus Oracle Server iSQL*Plus Commands Query Output Formatted Report Features of SQL are:  It is a non-procedural language of ANSI standard  It is an English-like language Features of iSQL*Plus are:  It is accessible from a browser  It supports ad hoc entry of statements  It formats query output into a basic report  It can access local as well as remote databases  It controls environmental settings © SQL Star International Ltd. 58
  • 62. SQL Statements The SQL statements can be categorized with regard to their functionality. They are:  SELECT statements - used to retrieve data from the database.  Data Definition Language (DDL)- used to create and maintain the database structure. The DDL statements are:  CREATE  ALTER  DROP  RENAME  TRUNCATE © SQL Star International Ltd. 59
  • 63.  Data Manipulation Language (DML): used to manipulate data i.e. to add more data, update or remove data from the database. The DML statements are:  INSERT  UPDATE  DELETE  MERGE  Transaction Control Statements: used to manage changes made by using the DML statements. The transaction control statements are:  COMMIT  ROLLBACK  SAVEPOINT  Data Control Language (DCL): used to secure the database. The DCL statements are:  GRANT  REVOKE Features of a SELECT Statement Using the SELECT statement, the following tasks can be achieved:  Selection (or restriction): Using this feature you can retrieve only those rows in a table that you want the query to return. For example, a Manager may be interested in retrieving details of those employees who report to him. To selectively restrict retrieval of rows, there are SQL clauses, which will be covered in the subsequent chapter.  Projection: Using this feature you can choose to retrieve only those columns in a table that meet your requirement. For example, an accountant would be interested in dealing only with the salary details of the company‘s employees. He would not choose to retrieve details such as their DOB, educational qualifications and their address.  Join: Generally, (most of the time) data from more than one table is required to be retrieved. This task can be achieved by creating links between the tables from which data need to be retrieved and presented as combined data. Basic Parts of a SELECT Statement © SQL Star International Ltd. 60
  • 64. There are two parts that are mandatory in a SELECT statement. They are:  The keyword SELECT (SELECT clause) followed by the columns that you want to see.  The keyword FROM (FROM clause) followed by the table name from which the columns have been specified in the SELECT clause. The syntax of a simple SELECT statement is SELECT {* | ,(column,)...} FROM table; Where, *(Asterisk) is used to select all the columns from a table column is used to select those columns specified after the SELECT statement table specifies the table from which the columns are to retrieved ; is the termination character. The SQL statements are executed immediately on encountering this character. Guidelines for Writing SQL Statements There are certain rules and guidelines to be followed while constructing SQL statements:  SQL statements are not case sensitive.  Enter SQL statements on one or more lines.  Cannot split or abbreviate keywords.  Place clauses on separate lines for better readability and editing.  Typically enter all keywords in uppercase, tablename in Initcap and all the words following them, such as column names, in lowercase.  At the end of the last clause place a semicolon (;). Writing a SELECT Statement © SQL Star International Ltd. 61
  • 65. Write SELECT statements to: Select all columns In order to retrieve all the columns from a table, you need to either place an asterisk (*) or list all the columns of the table after the SELECT keyword. For example, to retrieve all the columns from the Category table the following SELECT statement is issued in iSQL*Plus: SELECT * FROM CATEGORY; On issuing the statement, the following result is generated: -------------------------- 14 rows selected.  Select specific columns In order to retrieve only specific columns of a table, you need to list the columns in the order that you want to see in the output. For example, to retrieve member’s last names, their age and membership dates the following SELECT statement is issued in iSQL*Plus: SELECT cLastName, nAge, dMembershipDt FROM Member; On issuing the statement, the following result is generated: © SQL Star International Ltd. 62
  • 66. ---------------- 21 rows selected. From the query result you will observe that in iSQL*Plus:  Default column heading justification is: Center  Default column heading display is: Uppercase On the contrary, in SQL*Plus (as shown below):  Character and date column headings are justified to the left  Number column headings are justified to the right  Default column heading display is uppercase © SQL Star International Ltd. 63
  • 67. Refining Retrieved Data On extracting data using the SELECT statement, you get the output exactly the way it has been stored in the database. Oracle provides ways to refine retrieved data, that is, to modify the way the data is displayed, by suppressing duplicate data display, by performing some calculations or changing the column names. Using the DISTINCT Keyword The result of a request for data from a table would be without eliminating any duplicate rows. To suppress duplicate rows use the DISTINCT keyword in the SELECT clause. For example, an attempt to retrieve book names from the Book table would result in the retrieval of duplicate book names. This is because, the same books are stored in all the branches of the New Jersey Central Library. Therefore, to retrieve the distinct book names issue the following SELECT statement: SELECT DISTINCT cBookName FROM Book; On issuing the statement, the following result is generated: ---------------- © SQL Star International Ltd. 64
  • 68. 46 rows selected. You can specify multiple columns after the DISTINCT keyword. It would affect all the columns selected and return a distinct combination of the columns selected. For example, to retrieve unique combinations of the year of publish of books and the book names, issue the following SELECT statement: SELECT DISTINCT dPublishedYr, cBookName FROM Book; ------------------------ 48 rows selected. Using Arithmetic Operators All the basic arithmetic operators are available in Oracle, thereby enabling arithmetic calculations to be performed on the selected data. List of Arithmetic Operators © SQL Star International Ltd. 65
  • 69. Arithmetic operators can be used in any clause of a SQL statement except the FROM clause. For example, suppose the library decides to see the result on incrementing the number of copies of every book in each branch by two. This could be done easily with the use of arithmetic operation as shown below: SELECT DISTINCT cBranchID, cBookName, nNoOfCopies, nNoOfCopies+2 FROM Book; --------------- -------------- -------------- -------------- 181 rows selected This example uses the addition operator to increase the number of copies of each book. In the above result nNoOfCopies+2 is not a new column in the Book table. It is just for display and by default gets the name from the calculation performed, which in this case is nNoOfCopies+2. But this name is not very descriptive. Hence, Oracle provides a way to rename column headings to make them more descriptive and clear. Renaming Column Headings When you issue a SELECT statement, iSQL*Plus / SQL*Plus displays the column headings, which are the same as the names of the columns selected. But, this heading may not always be descriptive especially when calculations have been performed. So, Oracle provides you the option to change the column headings by using column aliases. By doing so, you can hide the business logic from others by giving a descriptive name to the column specially during a calculation. Alias headings appear in uppercase by default. © SQL Star International Ltd. 66
  • 70. How to Define a Column Alias? A column alias is defined as follows:  In the SELECT list, specify the column alias immediately after the column name using the keyword ‗AS‘ or a space between the column name and the alias.  Enclose the alias in double quotation marks (― ‖) if it contains spaces, special characters such as # or $, or if it needs to be case sensitive. In the SELECT statement wherein you had performed an arithmetic calculation, by default the heading of the column that displayed the calculated result was nNoOfCopies+2. Give this column a more meaningful name by defining an alias as follows: SELECT DISTINCT cBranchID, cBookName, nNoOfCopies, nNoOfCopies+2 “Post Increment” FROM Book; Displays: ------------------------------------ 184 rows selected. In the above SELECT statement, the calculated column has been assigned an alias without the use of the AS keyword. Whether the AS keyword is used or not, the query result remains the same. As the aliases contain spaces, they have been enclosed within double quotes. So, giving column aliases has made the calculated column more descriptive. Arithmetic operations follow some rules of precedence. Rules of Precedence If there is more than one operator used in an arithmetic expression, then operator precedence comes into picture. In operator precedence, multiplication and division © SQL Star International Ltd. 67
  • 71. take precedence over addition and subtraction. If operators having the same priority are there within an expression, then they are evaluated from left to right. Suppose, the New Jersey Central Library wants to increase its total earnings by way of membership fee. Assuming that at least 10 persons belonging to each grade enroll as members of the library every year, the proposed earnings would be as follows: SELECT cGrade grade, nFeeAmount+20 “Revised fee/member”, 10*12*nFeeAmount+20 “Proposed Earnings” FROM MemberFee; On the issue of the above query, the following result is displayed: The above statement displays three columns: Grade, Revised fee/member and Proposed Earnings. This SELECT statement calculates the revised fee to be paid by each member (nFeeAmount+20) and the proposed earnings for the entire year assuming each grade has 10 new members enrolled (10*12*nFeeAmount+20). You will notice that in the expression 10*12*nFeeAmount+20, multiplication is performed before addition. Since, there are two multiplication operations, they are performed from left to right. In order to override the rules of precedence, you can use parentheses. The expression within the parenthesis would be evaluated first. We shall override the precedence in the above statement using parentheses as follows: SELECT cGrade, nFeeAmount+20 “Revised fee/member”, 10*12*(nFeeAmount+20)“Proposed Earnings” FROM MemberFee; On the issue of the above query, the following result is displayed: In the above SELECT statement, parentheses have been used to cite the order in which the operations are to be performed. The SELECT statement calculates the proposed yearly income by incrementing the fee amount by 20 and then multiplying the result by 12 (12 months) and 10 (assuming 10 members enroll in each grade). © SQL Star International Ltd. 68
  • 72. While using arithmetic operations there are certain aspects you must be aware of. For instance, the role DUAL table plays, in performing arithmetic operations and the result of an arithmetic operation that involves a null value. Role of the DUAL Table Until now the arithmetic calculations you have performed were all based on numeric values extracted from database tables. But you may not always want to perform calculations on data from a table. For instance, you may want to perform some calculations on values not part of any table. In such a case, the Oracle server does not have any real table to extract data from. But, it is mandatory to specify column names after the SELECT keyword and a table name after the FROM keyword (that is, every SELECT statement must have a FROM clause). Therefore, why not extract data from a dummy table? The Oracle server provides a table called DUAL which will serve the purpose of satisfying the FROM clause. The DUAL table does not have any meaningful data. It contains one column called DUMMY with one row having a value ‗X‘. For example, the DUAL table is used to perform arithmetic calculations on constant values as shown below. SELECT 6788+2292 FROM DUAL; NULL Values and Arithmetic Operations If a particular column of a row does not have value, that value is called null. It is not the same as zero or a space, for zero is a number and a space is a character. Care needs to be taken while performing arithmetic operations on columns that have null values because they result in null. For example, suppose the library intents to increase its earnings by way of incrementing the fine charged to $2 from $1.5. To depict its future earnings the following statement is written: SELECT nFine Fine, nFine +(1.5*0.25) ―proposed fine earnings‖ FROM Transaction; The query displays the following result: © SQL Star International Ltd. 69
  • 73. The result shows some null values in the proposed fine earnings column. This is because the nFine column values for some rows are null. Using the Concatenation Operator In addition to performing arithmetic calculations or changing column headings, you can also join two or more columns to further refine (or change) the query result. Concatenation is the method used to join two or more column outputs into one, to produce more descriptive output. The resultant column is a character expression. It is advisable to give an alias to the resulting column. The concatenation operator is ( || ) two pipe characters put together. You can join columns to  Other columns  Arithmetic expressions  Constant values For example, while retrieving details of members from the Member table, it would be more appropriate to join the cFirstName and the cLastName columns to produce a single member name column. SELECT cFirstName||cLastName AS NAME FROM Member; On the issue of the above statement, the following result is displayed: --------------------------- © SQL Star International Ltd. 70
  • 74. 21 rows selected. The above SELECT statement has joined the first name and the last names of members using the concatenation operator. What are Literal Character Strings? A literal character string refers to any character, number or date included in the SELECT statement, but which is neither a column name nor a column alias. They are printed for each row returned by the query. Date and character literals need to be enclosed within single quotation marks (‗ ‘) but not number literals. For example, while retrieving the distinct book names along with their respective authors from the Book table, concatenate the two columns with a literal to make each row returned by the query more meaningful. SELECT DISTINCT (cBookName ||‘written by ‗ ||cAuthorName) AS ―Book Details‖ FROM Book; On the issue of the above statement, the following result is displayed: 49 rows selected. Alternative Quote (q) Operator The usage of character literals becomes obvious in many SQL SELECT statements or select expressions. Use an (q) operator if the literal itself contains a single quotation mark. This operator allows the developer to choose customized quotation mark delimiter. You can choose from a variety of delimiters, single-byte or multi-byte, or one of the following character pairs: [ ], { }, ( ), or < >. The following example will further explain the use of this operator: SELECT department_name || q‘[, it‘s assigned Manager Id: ]‘ || manager_id AS ―Dept and Mgr‖ FROM Departments; © SQL Star International Ltd. 71
  • 75. In the example shown, the string contains a quotation mark, which is interpreted as a delimiter. Using the q operator, the brackets [] are used as the quotation mark delimiter. The string between the brackets delimiters is interpreted as a literal character string. Using Script Files The statements entered in the Enter Statements field of iSQL*Plus can be saved to text files (known as script files) as follows: 1. Enter the SQL statement in the Enter Statements field, and click the Save Script button. 2. Select Save this file to disk radio button from the file download dialog box. Specify a file name and save it as shown below. © SQL Star International Ltd. 72
  • 76. To use the saved script: 1. Type the script name and location in the File field as shown below or click the Browse button to find the script file name and location. 2. Click the Load Script button to load the file contents into the Enter Statements field of iSQL*Plus. © SQL Star International Ltd. 73
  • 77. 3. Click the Execute button to run the file contents. DESCRIBE Command: It is an iSQL*PLUS command used to display the structure of a table. The syntax for the DESCRIBE command is DESCRIBE tablename Let us look into the following example and the output it generates, to discuss this in details. DESCRIBE Member The Describe command gives us the information about: COLUMN NAME - Name of the columns in the order it was created. NULL - Where the column can hold null value or not. DATATYPE - Column data could be of any of the following types: Character type Character datatypes represent all letters, numbers and special characters on the keyboard. Following are some of the character datatypes: VARCHAR2 holds a character data of variable length with a default minimum size 1 and maximum size 4000. © SQL Star International Ltd. 74
  • 78. CHAR holds a character data of fixed length with a default minimum size 1 and maximum size 2000. LONG holds Character data of variable length up to 2 gigabytes. For example, names of members in the Member table are of CHARACTER datatype. Number type The datatype used to store only numeric data is the number datatype, NUMBER (precision, scale). It can store both fixed and floating-point numbers. By precision we mean the total number of digits and scale is the number of digits to the right of the decimal point. For example, 779.69 is number datatype where the precision is 5 and the scale is 2. In the Member table, member‘s age is stored as NUMBER datatype. Datetype In Oracle, date data are stored in the DATE datatype, which actually contains two values: the date, and the time between January 1, 4712 BC and December 31, 9999 AD. The default date format in which Oracle stores date is DD-MON-YY where DD is the day of the month (01), MON is the month (Jan) and YY is the year (two-digit year-99). Summary In this chapter, you have learnt that: To retrieve data from the database, a SELECT statement is used. SQL statements can be executed in either SQL*Plus environment or iSQL Plus environment where, iSQL Plus is a browser environment introduced in Oracle9i. SQL statements can be categorized into: SELECT statement- to extract data Data Definition Language- To create data © SQL Star International Ltd. 75
  • 79. Data Manipulation Language- To modify data Transaction Control Language- To manage transactions done using DML Data Control Language- To control data access You can either select all columns of a table (using SELECT *) or select only specific columns of a table (using the column names) . To eliminate redundant data from the output, DISTINCT keyword is used. Column names can be given aliases to make them meaningful.  DUAL is a dummy table used for arithmetic calculations.  Use of operators like Concatenation helps to refine the retrieved data. Lab Exercise 1. Begin an iSQL*Plus session using the username and password provided to you by your instructor. 2. Display the structure of the Departments table. Select all the rows from the Departments table. 3. Display the structure of the Employees table. Write a query to retrieve the employee ID, first name, last name, job ID, hire date, department ID, and salary from the Employees table. Save the query to script file. Name the file as LabEx03_03.sql. 4. Look at the following SELECT statement. Can you identify any coding errors? SELECT Employee_ID, First_Name, Job_ID Salary x 0.1 Raised Salary FROM Employees; Execute the above statement and observe the error messages displayed. 5. Write a query to display the unique department numbers and job IDs from the Employees table. © SQL Star International Ltd. 76
  • 80. 6. Write a query to display the last name, job ID, salary and annual compensation of each employee. The annual compensation is to be calculated by adding a bonus of $500 to monthly salary, and then multiplying the result by 12. The query should combine the last name and job ID to make a single column named as ‗Employees‘. Give an alias ‗Annual Compensation‘ for the calculated column. The query should display the result as follows: 7. Copy the contents of LabEx03_03.sql file into the iSQL*Plus Edit window and make the following modifications:  Name the Employee_ID column as ‗Emp_No‘  Concatenate first name and last name of employees separated by a space. Name the column as ‗Emp_Name‘  Name Department_ID column as ‗Dept_No‘ The query should display the result as shown below. 8. Write a query to display the following output: © SQL Star International Ltd. 77
  • 81. 9. Write a query to display the following text using q operator. Oracle’s quote operator © SQL Star International Ltd. 78
  • 82. Chapter 4 Enhancing Data Retrieval Restricting Data Using WHERE Clause Using Comparison Operators Working With Logical Operators Sorting Data © SQL Star International Ltd. 79
  • 83. Objectives At the end of this chapter, you will be able to: Use WHERE clause in the SELECT statement  Work with comparison operators  Work with Logical operators Use ORDER BY Clause © SQL Star International Ltd. 80
  • 84. Enhancing Data Retrieval A simple SELECT statement retrieves data for all the rows in a table. The rows retrieved are not in any specific order. You can restrict the rows to be retrieved and also specify the order of retrieval. There are two clauses available to accomplish these tasks. They are the WHERE clause and the ORDER BY clause. Restricting Retrieved Data You can retrieve only some rows from a table instead of all the rows depending on the requirement. For example, imagine how tedious it will be if you have to find out those members who have issued a particular book from a table containing data about hundreds and thousands of members. But this task could be simplified by singling out those rows that don‘t meet your criteria. This can be achieved by using the WHERE clause. Its syntax is: SELECT [DISTINCT] {* | column [alias]…} FROM table [WHERE condition(s)]; The WHERE clause comes after the FROM clause and it contains a condition, which may or may not be met. The WHERE clause condition is made up of three elements:  The column name  Comparison operators  The column values Rules for using the column values in the WHERE clause :  Enclose all character and date values within single quotation marks.  Column values (character values in particular) are case sensitive but column names are not. Therefore, ensure that in the WHERE clause the character values are entered in their right case (uppercase, lowercase or mixed case).  Date values are format sensitive. The Oracle server stores date in the default format, which is DD-MON-YY. Therefore, ensure that in the WHERE clause the date values are entered in this default format. Comparison Operators As the name suggests, comparison operators are used in the WHERE condition to compare one expression to another. Following are the comparison operators used: © SQL Star International Ltd. 81
  • 85. Using Comparison Operators Based on a query made by a member to display all the books written by ‗Enid Blyton‘, the following SELECT statement is issued: SELECT DISTINCT (cBookName) FROM Book WHERE cAuthorName = ‗Enid Blyton‘; The result of the query is: To illustrate the usage of other operators look at the example given below. For the purpose of preparing a report, which shows the IDs of all those members, who are above the age of 21, the following SELECT statement is issued: SELECT cMemberID FROM Member WHERE nAge >21; The result of the above query is: © SQL Star International Ltd. 82
  • 86. Similarly you can use >=, <, <= and <> operators in the WHERE clause. Along with these operators there are other comparison operators such as,  The BETWEEN operator  The IN operator  The LIKE operator  The IS NULL operator BETWEEN Operator Using the BETWEEN operator, you can extract rows which fall within the range of values specified. The operator comprises of a lower range and an upper range. The lower range must be specified first. Both the values specified in the operators are inclusive. For example, the following statement is written in order to satisfy a member‘s query regarding details of all those books published between 1965 and 1980: SELECT DISTINCT (cBookName) FROM Book WHERE dPublishedYr BETWEEN ‘01-JAN-1965' AND ‘31-DEC-1980'; IN Operator When you use the equal to (=) operator, you are equating an expression with a value. Whereas, in case of the BETWEEN...AND…operator a range of values is specified. But, if you need to compare an expression to a list of values (may be the first, third, tenth and sixteenth values), then you need to use the IN operator. The IN operator specifies a list of values, which could be of any datatype. © SQL Star International Ltd. 83
  • 87. For example, to retrieve details of those books written by ‗Shakespeare‘, ‗Nora Roberts‘, and ‗Mary Higgins Clark‘, issuing the following SELECT statement would result in an error: SELECT DISTINCT(cBookName) FROM Book WHERE cAuthorName = ‗Shakespeare‘, ‗Nora Roberts‘, ‗Mary Higgins Clark‘; Following is the error message displayed when the statement is executed: * ERROR at line 3: ORA-00933: SQL command not properly ended The SELECT statement resulted in an error because the ‗=‘ operator is used only to equate one value. Hence, rewrite the statement using the IN operator. SELECT DISTINCT(cBookName) FROM Book WHERE cAuthorName IN(‗Shakespeare‘, ‗Nora Roberts‘, ‗Mary Higgins Clark‘); The result of the query is: LIKE operator You may not always remember the exact value you are looking for in the database tables. To overcome this problem, Oracle has provided the LIKE operator wherein you can retrieve those rows that match the character pattern specified in the operator. The method of matching expressions to a character pattern is called a wildcard search. Following are the symbols used to create a character pattern: % :- Sequence of zero or more characters preceding the character specified before the symbol. Example, To extract member names starting with A, use LIKE ‗A%‘ in the WHERE clause. _ :- Any single character preceding the character specified before the symbol. For example, to extract those member details who have the second letter in their names as alphabet ‗a‘, use LIKE ‗_a%‘ in the WHERE clause. SELECT cFirstName||cLastName ―Member Name‖ FROM Member WHERE cFirstName LIKE ‗_a%‘; © SQL Star International Ltd. 84
  • 88. The query gives the following result: But suppose you need to have an exact match for the actual symbols ‗%‘ and ‗_‘, and then you need to use the ESCAPE option. In this option you need to specify what the ESCAPE character would be. For example, suppose one of the branch names of the library that needs to be queried is ‗Dover_Brnc‘, then your ESCAPE option would be as follows: SELECT cBranchID, cBranchName, cBranchLocation FROM Branch WHERE cBranchName LIKE ‘%_%’ ESCAPE ‘’; And the result set would be: CBRANCH CBRANCHNAME CBRANCHLOCATION ------- ----------- --------------- 06DOVNJ Dover_Brnc Dover In this SELECT statement the ESCAPE option specifies the escape character to be backslash (). Since the escape character precedes underscore (_), it causes the Oracle server to interpret the ‗_‘ literally causing the statement to retrieve details of branch ‗Dover_Brnc‘. IS NULL Operator Since a NULL value stands for anything that is unavailable or unknown, you cannot use the (=) operation because null cannot be equal or unequal to any value. So, you have the IS NULL operator to test for null values. For example, the library resolves to bestow certain facilities such as extending the due dates of all those members who are punctual in returning books. To identify these members the following SELECT statement is issued: SELECT cMemberID FROM Transaction WHERE nFine IS NULL; Which displays: © SQL Star International Ltd. 85
  • 89. 12 rows selected. The statement retrieves those members who have not paid any fine amount. Logical Operators So far in the WHERE clause you have used only one condition. But, with logical operators you combine conditions. Two or more conditions are joined together to produce a single output by using the following logical operators:  AND  OR  NOT AND Operator © SQL Star International Ltd. 86
  • 90. If the desired rows are to be selected, then both the conditions specified in the WHERE clause must necessarily evaluate to TRUE. For example, to retrieve only those books that are stored in branch ‗04RANNJ‘ and which were published in the years ranging from 1965 to 1980, a SELECT statement using the AND operator needs to be written as shown below. SELECT cBookName FROM Book WHERE dPublishedYr BETWEEN ‘01-JAN-1965' AND ‘31-DEC-1980' AND cBranchID = ‘04RANNJ‘; The query displays the following result: If a member has not paid fine, it does not necessarily mean that he has returned the borrowed books on the due dates. This is because the nFine column of a member whose due date is yet to come will also be null. Hence, to find out those members who have not defaulted, the following SELECT statement using the NOT operator is to be written as shown below. SELECT cMemberID FROM Transaction WHERE nFine IS NULL AND dActualReturnDt IS NOT NULL; The result of the query is: 9 rows selected. By using two conditions in the WHERE clause, the above statement returns those members who have returned the borrowed books on their due dates. The two conditions are:  To retrieve the IDs of those members who have not paid any fine and © SQL Star International Ltd. 87
  • 91.  To retrieve the IDs of those members who have returned the borrowed books. The above statement uses the logical operator NOT in the WHERE clause as follows: AND dActualReturnDt IS NOT NULL The NOT operator specifies that the date on which the member returned his books is not null (that is, he has returned the books). The result of joining two expressions using the AND operator is given using the AND TRUTH table. OR Operator In order to select the desired rows, either of the conditions specified in the WHERE clause can be TRUE. For example, to retrieve books written either by ‗Nora Roberts‘ or those that belong to the ‗mystery‘ category, the following statement is issued: SELECT DISTINCT(cBookName) FROM Book WHERE cAuthorName = ‗Nora Roberts‘ OR cCategoryID = ‘01MYS‘; The result of the query is as follows: The result of joining two expressions using the OR operator is given below using the OR TRUTH table. © SQL Star International Ltd. 88
  • 92. NOT Operator Operators such as BETWEEN, IN, LIKE and NULL can be used along with the NOT operator. You have already seen its usage in one of the examples above. Here is another one. For example, the library database user issues the following statement in order to display those books not written by ‗Robert Louis Stevenson‘ and ‗Michael Crichton‘: SELECT DISTINCT(cBookName) FROM Book WHERE cAuthorName NOT IN (‗Robert Louis Stevenson‘, ‗Michael Crichton‘); The result of using the NOT operator in a condition is given in the NOT TRUTH table. Order of Evaluation The order in which the operators are evaluated are: /This order of evaluation can be overridden using parentheses. An example illustrating the rules of precedence: SELECT cBookName FROM Book WHERE cBranchID =‘01ADLNJ‘ AND cAuthorName = ‗Charles Dickens‘ OR nNoOfCopies = 2; © SQL Star International Ltd. 89
  • 93. The query result is as follows: ---------------------------- 24 rows selected In this example there are two conditions:  The first condition mentions that branch ID must be 01ADLNJ and author must be ‗Charles Dickens‘.  The second condition mentions that the quantity of books stored must be 2. But, to retrieve those books written by ‗Charles Dickens‘ and stored in branch ‗01ADLNJ‘ or those books whose quantity stocked is 2,the above example could be re- written as below: As per the rule of precedence, the AND condition has a priority over the OR condition. You can override this by using parenthesis as shown in the following statement: SELECT cBookName FROM Book WHERE cBranchID = ‘01ADLNJ‘ AND (cAuthorName = ‗Charles Dickens‘ OR nNoOfCopies = 2); Which gives the result: Now, the two conditions in this example are:  The author must be ‗Charles Dickens‘ or the number of copies must be 2.  The branch ID must be ‗01ADLNJ‘. © SQL Star International Ltd. 90
  • 94. Sorting Retrieved Data Data stored in the tables do not follow a particular sequence. They are neither sorted in the ascending nor descending order of precedence. You can use the ORDER BY clause to fetch rows in a specific order. The ORDER BY clause is the last clause in the SELECT statement. The syntax for using the ORDER BY clause is: SELECT <column_name>… FROM <table_name [WHERE condition(s)] [ORDER BY {column, expr} [ASC | DESC] ]; Where, ORDER BY clause is used to sort the rows to be fetched. ASC specifies that the rows are to be sorted in the ascending order, which happens to be the default order. DESC specifies that the rows are to be sorted in the descending order. When you issue a SELECT statement to retrieve member details from the Member table, the resulting rows are not in any sequential order. SELECT cMemberID, nAge FROM Member; The query gives the following result: ------------------ 21 rows selected. But if you want to retrieve member details sorted according to their ages, issue the following SELECT statement: SELECT cMemberID, nAge FROM Member ORDER BY nAge; The query gives the following result: © SQL Star International Ltd. 91
  • 95. ------------------ 21 rows selected. This statement displays all the members sorted according to their ages. The rows are sorted in ascending order, as it is the default way of sorting. The ascending order of sorting for different datatypes is as follows:  Number data values are fetched with the lowest values first.  Character data values are fetched in the alphabetical order from A to Z.  Date data values are fetched with the earliest date first. For example, 17-OCT-97 will be displayed before 17-OCT-99.  Null values are fetched last. In order to reverse the default sorting order, you need to specify the DESC keyword after the column name in the ORDER BY clause. The above statement had retrieved details from the Member table beginning from the junior most (age wise) members. To retrieve the details of the senior members, issue the following statement: SELECT cMemberID, nAge FROM Member ORDER BY nAge DESC; The result of the query is: ----------------------------- 21 rows selected. In case an alias has been assigned to the column based on which you intend to sort the result, then you can use the column alias in the ORDER BY clause. SELECT cMemberID,nAge,dMembershipDt ―Membership Date‖ FROM Member ORDER BY ―Membership Date‖; © SQL Star International Ltd. 92
  • 96. The result of the query is as follows: ------------------------ 21 rows selected. In the ORDER BY clause, you can specify more than one column each separated using commas. For example, to display the names of the library members sorted according to their membership dates and age, the following statement is issued: SELECT cMemberID, cFirstName, cLastName FROM Member ORDER BY dMembershipDt, nAge DESC; The result of the query is: -------------- 21 rows selected. This statement orders the result by membership date and then by descending order of members‘ age. One interesting aspect that comes out of this example is that you can sort by columns not specified in the SELECT clause. Neither dMembershipDt nor nAge columns based on which the result has been sorted have been specified in the SELECT clause. © SQL Star International Ltd. 93
  • 97. Summary In this chapter, you have learnt that:  Use of WHERE clause in a SELECT statement lets you to retrieve only the required data and ORDER BY clause arranges the retrieved data in a specific order.   Comparison operators such as BETWEEN..AND, LIKE, IN, IS NULL along with relational operators (>, <, <=, >= etc) and logical operators (AND,OR,NOT) can be used in the WHERE clause condition to restrict the output.  ORDER BY clause sorts the data either in ascending or descending order using keywords ASC and DESC respectively.   Column specified in the ORDER BY clause need not be mentioned in the SELECT clause of the query. Lab Exercise 1. Write a query to display details of employees whose job ID is ‗ST_CLERK‘. 2. Write a query to display last name, job ID, department number and salary of employees whose salary is greater than $14,000. 3. Write a query to display last name, department number and hire date of employees hired between 01-JAN-1995 and 31-DEC-1999. Sort the query in descending order of hire date. 4. Write a query to display the employee ID, first name and manager ID of employees whose manager ID is 100, 108, 148 or 120. 5. Write a query to retrieve the last name and hire date of employees hired in 1997. 6. Write a query to retrieve the employee ID, last name and job ID of employees whose job ID contains the string ‗SH_‘. 7. Write a query to retrieve the first name, job ID and Department number of employees who do not have a manager. 8. Write a query to retrieve the employee ID, last name, salary and commission of all employees who earn a commission. Sort the query result in descending order of salary. 9. Write a query to retrieve the last name, department number, job ID and salary of employees if, the job ID is ‗SA_MAN‘ or ‗SA_REP‘, and if the employee earns a salary more than $10,000. The query result should be as shown below: © SQL Star International Ltd. 94
  • 98. 8 rows selected. 10. Write a query to retrieve the last name, job ID, department number and salary for employees whose department ID is 50 or whose job ID contains the string ‗MAN‘. The query result should be as shown below: 11. Write a query to display the details of employee whose last name is ‗ernst‘. © SQL Star International Ltd. 95
  • 99. Chapter 5 Generating Formatted Reports using iSQL*PLUS Substitution Variables Using Pre-Defined Variables Producing Formatted Reports Using FORMAT Commands Creating Formatted Script Files © SQL Star International Ltd. 96
  • 100. Objectives At the end of this chapter, you will be able to:  Write queries requiring user input  Format the output using the various iSQL*PLUS commands  Create script files to run reports © SQL Star International Ltd. 97
  • 101. iSQL*Plus Substitution Variables SQL comprises of statements that are entered into the command line. On encountering an SQL statement, the Oracle server‘s SQL processing mechanism returns the required data. After returning the data, it is ready to execute the next statement that is entered. For example, in order to retrieve the address details of a member with ID ‗DDG019503‘, you must issue the following SELECT statement: SELECT cFirstName||cLastName Name, vAddress, cArea FROM Member WHERE cMemberID = ‗DDG019503‘; On encountering this statement, the Oracle server returns the data that corresponds to the cMemberID value specified in the WHERE clause. On running the above query again, the Oracle server returns the same data because its range is predetermined by the fixed WHERE clause of the query. This query will not hold good if the librarian wants to retrieve address details of any other member. Therefore, the query issued is not interactive. It could be made interactive by enabling the librarian to enter values that determine the range of data to be returned, at runtime. Oracle server‘s SQL processing mechanism contains features that enable users to specify their own values to restrict the range of data to be retrieved at runtime. This is achieved by using iSQL*Plus substitution variables (also known as runtime variables). Substitution Variables Several times when developers execute a query, they do not know what value the user may want to use to restrict the range of data to be returned. Therefore, they hard code the value into the statement. However, it is cumbersome when the same query is issued each time with a different value to restrict the range of data to be retrieved. For instance, when the librarian extracts the address details of a member with ID as ‗DDG019503‘, the cMemberID column value is hard coded in the WHERE clause. However, if he uses the same statement to extract address details of a member with ID as ‗DCF058502‘, he would be unable to do so. To make the statement reusable and flexible, substitute the hard-coded member ID value with a variable that prompts the user to enter different member ID values each time the statement is executed. These variables are known as substitution variables. © SQL Star International Ltd. 98
  • 102. In iSQL*Plus environment, single-ampersand (&) substitution variables are used to store temporary values. The statement used to retrieve data from the Member table based on the hard- coded member ID value can be rewritten by using the substitution variable (&) as follows: SELECT cFirstName||cLastName Name, vAddress, cArea FROM Member WHERE cMemberID=‘&MemID‘; In the statement, the MemID variable is prefixed with a single ampersand (&). Doing so, informs the Oracle server that the user should be prompted for a member ID value each time the statement is executed. The output is: On entering the member ID value, the query displays the name and address for that member. © SQL Star International Ltd. 99
  • 103. Now the SQL statement is a flexible statement, therefore, you can re-execute it by specifying a different member ID value at run-time. You can verify the changes made on re-executing the statement by using the SET VERIFY command. Setting SET VERIFY ON displays the value before and after it is replaced by the substitution variable. Before a variable is replaced by the user- provided value, the old value is always the variable itself. Points to remember while using substitution variables:  Enclose substitution variables within single quotes if they are used to store character or date values. If they are used to store number datatypes, single quotes are not required. For example, … WHERE cMemberID = ‘&MemID’;  Functions such as UPPER and LOWER can be used with substitution variables. For example, using UPPER(‗&BkName‘) indicates that the user need not enter the book name in uppercase.  You can use substitution variables not only in the WHERE clause but also in the following clauses: The ORDER BY clause Column names in the SELECT clause Table name in the FROM clause Use substitution variables in the ORDER BY clause when you want to sort the result of a query on the Book table according to a column of your choice. SELECT cBookID,cBookName,&ColumnName FROM Book WHERE &Condition ORDER BY &SortingColumn; On executing the statement, the book ID, book name and any other column that the user specifies at runtime into the ColumnName substitution variable, is displayed. These columns are retrieved by the condition the user specifies into the Condition substitution variable for their retrieval and the column by which the retrieved data is to be sorted. © SQL Star International Ltd. 100
  • 104. © SQL Star International Ltd. 101
  • 105. The output is: Many times a user may want to use the same variable value more than once without being prompted for a value each time. © SQL Star International Ltd. 102
  • 106. For example, the librarian may want to retrieve book details sorted by the same column he specifies for the substitution variable. But by using single-ampersand substitution variable, each time he re-executes the statement, he would be prompted for the column value with which the data is to be sorted. In order to be prompted for a value only once, the double ampersand (&&) substitution variable is used in the following manner: SELECT cBookID,cBookName,&ColName FROM Book ORDER BY &&Column; Re-executing the above statement retrieves book Ids, book names and any other column that the librarian specifies to be placed in the single ampersand ColName substitution variable. But each time, the retrieved columns are sorted according to the same column he specifies in the double ampersand Column substitution variable. Yet, entering new values for single ampersand variables or using the same value that is placed into the double ampersand variable may not always be useful. For example, the values entered into the ColName can be used only in the statement in which they have been defined. Once the variable value is used, iSQL*PLUS discards it, thereby, requiring you to enter a new value each time. Instead of running the statement over and over again so as to enter new values, you could predefine variables with values before executing the statements. This is done by using two iSQL*PLUS commands: DEFINE and ACCEPT. Predefining variables The two iSQL*Plus commands used to predefine variables are:  DEFINE  ACCEPT The DEFINE Command Values for runtime variables are defined by using the DEFINE command. The command defines the input value of a variable before executing any statement. Therefore, unlike substitution variables, any statement can use them, as the value is not discarded once it is used in that session. In case the library desk officer wants to make queries about information on books from the Book table and from the Transaction table, she may do so by using a substitution variable for accepting the ID of the book. SELECT cBookName Books FROM BOOK WHERE cBookID=‘&BookID‘; © SQL Star International Ltd. 103
  • 107. The output is: The disadvantage of this query is that other SELECT statements cannot use the substitution variable used in the above SELECT statement. Therefore, the DEFINE command can be used to avoid entering values for variables each time the statements are run. It assigns a value to a CHAR datatype variable that gets created. The DEFINE command is issued with the following syntax: DEFINE <variable_name> = value To enhance the above statement, issue the DEFINE command in the Enter Statement field and click the Execute button. DEFINE BookID = ‗MYS040000068‘ To display the values in a variable, use the command with the variable name as shown. DEFINE <variable_name> DEFINE BookID The above command displays the following result: DEFINE BOOKID = ―MYS040000068‖ (CHAR) The value you have defined into the BookID variable can now be used in any of the statements as follows: © SQL Star International Ltd. 104
  • 108. SELECT cBookName FROM Book WHERE cBookID=‘&BookID‘; Or you can issue SELECT cTranID,dIssueDt FROM Transaction WHERE cBookID=‘&BookID‘; The output is: The variables defined with this command remain throughout the session unless you undefine them. By un-defining the variables, they can be reused. To undefine the BookID, give the following command. UNDEFINE BookID You can confirm the change made, by issuing the DEFINE command. DEFINE BookID Displays: SP2-0135: symbol bookid is UNDEFINED ACCEPT Command: ACCEPT command requests value for a variable from the end user. Syntax: ACCEPT <variable_name> datatype Example: ACCEPT vage NUMBER © SQL Star International Ltd. 105
  • 109. SELECT * FROM Member WHERE nage=&vage; A variable declared using a DEFINE command is always of character datatype, whereas you can specify the datatype for a particular variable using ACCEPT command. Producing Formatted Reports When users execute queries they are presented the data, as it is stored in the tables. But reports need to be formatted so as to be more presentable and expressive. This is made possible by using:  SET commands  FORMAT commands Using SET Commands SET commands are used to control the session environment in which iSQL*Plus operates. Following is the syntax to set the session environment variables: SET <system_variable> value Where, system_variable is a variable that controls the session environment. value is the value of the session environment variable. For example, SET ECHO ON This command sets the value of the session environment variable ECHO to ‗ON‘. Later, you can verify the values of all the session environment variables that are set, using the SHOW command. For instance, you can check the value of the ECHO variable in the following manner: SHOW ECHO Displays: echo ON In order to verify all the system variables that have been set, use the SHOW ALL command. SET Command Variables © SQL Star International Ltd. 106
  • 110. As mentioned earlier SET command variables are used to control the environment of the current session. Following are the SET command variables: In the commands, the underlined values are the default values. n is a numeric value that the user enters. If no value is entered, iSQL*Plus considers the default value. For instance, set the system environment variable HEADING to OFF in the following manner: HEADING OFF Now select the records from the Member table giving the following query: SELECT * FROM Member; The output is: © SQL Star International Ltd. 107
  • 111. Notice that the heading is not displayed in the output. Using FORMAT Commands The SET commands help only to control the current environment settings. However, to format the report features such as determining the way columns should be displayed, or giving suitable headers and footers, use the FORMAT commands. The commands used to format reports are:  The COLUMN commands – to format column display  TTITLE and BTITLE commands– specify headers and footers that should appear on each page of the report  BREAK command – suppresses duplicate values and helps creating break reports Using the COLUMN Commands COLUMN commands control the way column data should be displayed. This is done by using the following options with the COLUMN command: © SQL Star International Ltd. 108
  • 112. The syntax for changing the way column data is display is: COL[UMN] [{column|alias}] [option]] Where, column|alias is the column whose data display is to be formatted option specifies the way the column data is to be formatted. The following commands are used to show or to clear the current column formatting: The column command options discussed above are explained here with the help of examples: HEADING Option This option sets the heading that appears for a particular column. For example, the heading of vAddress column could be changed to make it more meaningful in the following way: © SQL Star International Ltd. 109
  • 113. COLUMN vAddress HEADING ‗Member|Address‘ In the COLUMN command, the vertical line causes the word after it to be placed on the next line. On issuing a SELECT statement, you could see the result of the above setting. SELECT * FROM Member; The output is: ------------------- 21 rows selected. The NULL Option The NULL option specifies the text to be displayed for null values. For example, while preparing a report to display all the member details, the library clerk may not want nfine column to show any null values. Therefore, he could replace it with text using the NULL option as follows: COLUMN nFine NULL ‗No Dues‘ Issue the following SELECT statement in order to display the text written using the NULL option: SELECT cMemberID,nFine FROM Transaction; The following screenshot is the output: - © SQL Star International Ltd. 110
  • 114. ---------------- 32 rows selected. Notice the nFine column with null values is populated with the text ‗No Dues‘. NOPRINT and PRINT Option These options determine which columns are to be hidden or shown while preparing reports. For example, the librarian may not want the cGrade and nAge columns to be displayed while selecting all the columns from the Member table. To do so he could hide them by using the NOPRINT option as follows: COLUMN cGrade NOPRINT COLUMN nAge NOPRINT When you issue a SELECT statement specifying these two columns, they will not be displayed. SELECT cMemberID, cGrade,nAge FROM Member; Displays the following output: © SQL Star International Ltd. 111
  • 115. -------------- 21 rows selected. To display these columns, you can either clear the settings of both the columns using the CLEAR option or use the PRINT option as follows: COLUMN cGrade CLEAR COLUMN nAge PRINT Having cleared the NOPRINT option, check the output of the above SELECT statement. It displays all the columns specified in the SELECT statement. The FORMAT Option The FORMAT option enables the user to change the display of column data. There are different formatting models available to change the display of number data and character data. Number Formatting Model Formatting Description Example Result Character Specifies the display FORMAT 2020- width of the number of 9999 acceptable digits to be entered. If 152550- not there is a number acceptable. It 9 overflow, the Oracle returns Server displays ‗#‘. It 1525## suppresses any leading zeros Enforces the display of Format 789 0 leading zeros 0999 Places a dollar sign before $99,999 $59,590 $ the number © SQL Star International Ltd. 112
  • 116. Displays local currency L9999 Rs7878 L symbol before the number Specifies the position for 99,999 25,789 , placing a thousand separator Specifies the position of a 9999.99 4562.75 . decimal point and rounds appropriate Examples of some formatting models are: Column nFeeAmount FORMAT $999.99 SELECT nFeeAmount FROM MemberFee; Displays the following result: Using the TTITLE and BTITLE Commands The TTITLE and BTITLE commands are used to format page headers and footers respectively. The syntax for both the commands is identical: TTITLE|BTITLE [text| ON | OFF] Where, text represents what the page title or footer should be. Enclose the text in single quotes if it is more than a word. ON | OFF specifies whether the headers or footers are to appear on the report or not. For example, display a suitable header and footer for all the reports generated by the New Jersey Central Library. © SQL Star International Ltd. 113
  • 117. TTITLE ‗New Jersey Central Library | Weekly Book Issue Report‘ BTITLE ‗Confidential Report‘ SELECT cTranID,cMemberID,cBookID,dIssueDt FROM Transaction; The report displayed by the above statement is: ------------------------ 31 rows selected. The TTITLE command displays ‗New Jersey Central Library‘ centered on the first title line and ‗Weekly Book Issue Report‘ centered below it. The TTITLE command automatically displays the date and page number on every page in the report. The BTITLE command displays ‗Confidential Report‘ centered below every page of the report. You can use the words RIGHT and LEFT with BTITLE to right or left justify the text other than the center of the page. An enhancement over TTITLE and BTITLE is the REPHEADER and REPFOOTER commands. You have seen the default behavior of the TTITLE command. This is sufficient for most of your report generating activities. But, some reports © SQL Star International Ltd. 114
  • 118. would require more sophistication such as placing the clerk‘s name (who is preparing the report), or place page numbers at the specified position, etc. This is met by using the REPHEADER command. The REPHEADER command places a specified title at the top of each report and formats it. Its syntax is, REPH [EADER] [PAGE] [printspec [text| variable]...]|[OFF|ON] The syntax is the same even for REPFOOTER. Where, PAGE starts a new page after printing the specified report header or before printing the specified report footer. printspec represents one or more of the following clauses used to place the text and format it:  COL n - Indents to position n of the current line  S[KIP] [n] – determines the number of lines to be skipped. If you omit n, one line is skipped at a time; if you enter zero for n, the print position goes backward to the start of the current line.  TAB n - Skips forward n print position. If you enter a negative value for n, it skips backward.  LE[FT] CE[NTER] R[IGHT] – specifies how the text is to be justified.  BOLD - Prints data in bold print.  FORMAT text - Specifies a format model that determines the format of the data items. Refer to the FORMAT clause of the COLUMN command in this chapter  Text - Represents the report header or footer text. Enter text in single quotes if you want to place more than one word on a single line.  OFF - Turns the report header or footer off (suppresses its display) without changing its definition.  Variable – represents any of the following system generated variables like:  Sql.ino – specifies the current line number  Sql.pno – specifies the current page number  Sql.user – specifies the name of the user who has logged in to iSQL*PLUS environment. If you do not enter a printspec clause before the text or variables, REPHEADER left justifies the text or variables. To understand these advanced clauses, let us use them to make a more sophisticated header and footer. REPHEADER LEFT ‗Report generated by Brad Riley‘- SKIP CENTER ‗New Jersey Central Library‘- © SQL Star International Ltd. 115
  • 119. SKIP CENTER ‗Yearly Book Issue Report‘ REPFOOTER CENTER ‗COFIDENTIAL -REPORT‘ Now run the query: SELECT * FROM Transaction WHERE dIssueDt BETWEEN ‘01-JAN-2000' AND ‘31-DEC-2000'; It displays the following output: 10 rows selected. Using the BREAK Command The BREAK command is used to suppress duplicate values. To understand its usage, look at the result of the following query without using the BREAK command: © SQL Star International Ltd. 116
  • 120. SELECT cBranchID, cBookName, nNoOfCopies FROM Book ORDER BY cBranchID, cBookName; The output of the statement is: 184 rows selected. The query displays the books belonging to each branch. But you will notice that the branches‘ IDs are repeated. In order to suppress them, you should use the BREAK command. Its syntax is: BREAK ON column [ | alias ] BREAK ON cBranchID After issuing the above BREAK command, observe the result obtained by performing the following query: SELECT cBranchID, cBookName, nNoOfCopies FROM Book ORDER BY cBookName; © SQL Star International Ltd. 117
  • 121. ------------------ 184 rows selected. By issuing the BREAK command, the same query result changes. You will notice that the branch ID ‗01ADLNJ‘ is printed only in line 1 and is suppressed in lines 2 to 36, and from line 37 a different branch ID is printed. You will notice that the ordering of the query output by book name hampers the suppression of duplicate branch IDs. This is because you must always remember to order your query by the same column on which you have issued the BREAK command. But this report is quite incomplete without computing the total copies of books that each branch stores. To do this, you need to just mention what you want added up by using the COMPUTE command. You will have to re-format the above query by incorporating the COMPUTE command as follows: COMPUTE SUM OF nNoOfCopies ON cBranchID SELECT cBranchID, cBookName, nNoOfCopies FROM Book ORDER BY cBranchID, cBookName; The output is: © SQL Star International Ltd. 118
  • 122. ------------------ 184 rows selected. The COMPUTE SUM OF nNoOfCopies ON cBranchID forces the total number of copies for each branch to be printed only when a new branch ID is printed. Having used all the various commands to format your reports, you need to remember some important points:  All formatting commands remain in effect unless you end the current iSQL*PLUS session or overwrite them.  After every report, remember to reset the iSQL*PLUS settings to their default values.  There is no command available to reset the iSQL*PLUS settings to their default values. You must either know the default value or log out and log in again.  In case, you have assigned an alias for a column, then reference the alias name instead of the column name.  The entire standard SET commands, as well as, other iSQL*PLUS commands required for every session are stored in a file known as the login.sql. As soon as you CONNECT to a user in iSQL*PLUS environment, this file is read and all its commands are implemented. These settings can be changed during the current session. But they are in effect only for that session. Once you log out they are lost. Therefore, to make them permanent add these settings to the login.sql file. © SQL Star International Ltd. 119
  • 123. Creating Formatted Script Files All the iSQL*Plus commands you have covered so far could either be entered individually in the Enter Statement field or entered along with the SELECT statement into a script file (or command file). Creating a script file is recommended because all the formatting commands needed for the generation of a report could be kept in one place without having to enter them individually. You only need to run the script file for producing the result. You already know how to create script files. Now you will see further enhancements that can be made. However, before that you should understand the steps for creating script files. Create a Script File for Formatted Results The steps to be followed for creating script files are: 1. Issue a SELECT statement in the Enter Statement field and ensure that before you save it to a file, the data it retrieves is accurate. Include the ORDER BY clause if you intend to use the BREAK command. 2. Edit the script file and enter the formatting commands before the SELE statement. Ensure that you do not add them within the SELECT statement. 3. Add the format-clearing commands after the SELECT statement. 4. Save the changes made to the script file. In Oracle10g, you can have spaces in the filename or within the directory path by enclosing them fully with double quotes. Syntax to save a script in SQL*Plus: SQL> SAVE ― <filename>‖ Example: SQL> SAVE ―d:training classes my script.sql‖ 5. To execute the script file, click the Browse button, select the script file, and click the Load Script button. Once the script is loaded, click the Execute button. To run the above script in SQL*Plus, give the following statement: SQL> @ ―d:training classesmy script.sql 6. Use REM whenever you wish to add a remark or a comment in iSQL*Plus script file. Following the above steps, you can now create a script file to generate a report that displays the total number of copies of books stored in each branch. 7. The required SELECT statement is entered in the iSQL*Plus Enter Statement field. © SQL Star International Ltd. 120
  • 124. 8. Save the statement to a script file called REPORT 9. Edit the REPORT script file to add all the formatting commands SET PAGESIZE 200 SET LINESIZE 170 SET FEEDBACK ON REPHEADER OFF REPFOOTER OFF TTITLE ‗NEW JERSEY CENTRAL LIBRARY‘ BTITLE ‗CONFIDENTIAL REPORT‘ BREAK ON cBranchName COMPUTE SUM OF nNoOfCopies ON cBranchName COLUMN cBranchName HEADING ‗Branch|Name‘ COLUMN cBookName HEADING ‗Book|Name‘ COLUMN cAuthorName HEADING ‗Author|Name‘ COLUMN nNoOfCopies HEADING ‗Copies‘ REM Insert a SELECT statement here SELECT B.cBranchName, Bk.cBookName, Bk.cAuthorName, Bk.nNoOfCopies © SQL Star International Ltd. 121
  • 125. FROM Branch B, Book Bk WHERE B.cBranchID = Bk.cBranchID ORDER BY B.cBranchName; REM clear all the settings SET FEEDBACK OFF CLEAR COLUMN TTITLE OFF BTITLE OFF CLEAR BREAK 10. Execute the script file and observe the result. The report generated is more presentable as compared to the result generated on executing a SELECT statement without any formatting. 184 rows selected. columns cleared breaks cleared © SQL Star International Ltd. 122
  • 126. SPOOL Command In SQL*Plus, the output of a script can be directed to a file using SPOOL command. Syntax to use SPOOL command is : SQL> SPOOL <filename> SQL> SPOOL OFF Example: SQL> SPOOL d:test.txt SQL> SELECT * FROM Member; SQL> SPOOL OFF The output of the above SELECT statement is stored in a text file called test. In Oracle10g, new option called APPEND has been added to SPOOL command. It appends the output of a SPOOL command to an existing file. The above code can be re-written using APPEND command as SQL> SPOOL d:test.text APPEND SQL> SELECT * FROM Memberfee; SQL> SPOOL OFF In the test.txt file, the output of the above SPOOL command gets appended. SET SQLPROMPT New variables have been introduced to set the prompt in your SQL*Plus session with this release of 10g. _DATE : the current date or a pre-defined string. _PRIVILEGE : level of connection, SYSDBA, SYSOPER or NULL for normal. _USER : user you are connected to. Example SQL > SET SQLPROMPT ―_DATE : _USER‘@‘_CONNECT_IDENTIFIER _PRIVILEGE > ― 20-MAY-04 : SYSTEM@prd9i > © SQL Star International Ltd. 123
  • 127. If you want the column name in the condition to remain same each time you execute the query, use &&-double ampersand Substitution Variables. Variable can be pre-defined using DEFINE and ACCEPT command. DEFINE stores Character value by default. Datatype of a variable can be specified while using ACCEPT command. Lab Exercise 1. Display the Last Name, department and salary of the employees whose employee id is 105. Make the above query interactive. © SQL Star International Ltd. 124
  • 128. After Execution: 2.Write a query that prompts the user to specify the condition and the order by sorting column, using substitution variables. © SQL Star International Ltd. 125
  • 129. 6 rows selected. 3.Display employee details, by prompting the user to enter a column name he/she wishes to view. The user should be prompted only once for the sorting column. © SQL Star International Ltd. 126
  • 130. ------------------- 108 rows selected. 4. For the report above, display the heading ‗Employees Report‘ on the top of the page. (Give any name you like). Give a name for the person who generated the report. (You may use your own name.). Create a script file to generate employee Ids, first and last names, departments and job IDs and salaries of all employees sorted according to the department IDs. Format the report to include: a page size of 300 line size of 100 feedback off a title and subtitle for the report appropriate column headings word wrap format salaries to include decimals and thousand. © SQL Star International Ltd. 127
  • 131. Once the script is run and the report generated, ensure that all the settings are back to the default. © SQL Star International Ltd. 128
  • 132. Chapter 6 SQL Single RowFunctions Types of SQL Functions Features of Single Row Function Character functions - Case Manipulation and Character Manipulation Number and DATE Functions Conversion- IMPLICIT and EXPLICIT RR Date Format General Functions Use of Conditional Expression © SQL Star International Ltd. 129
  • 133. Objectives At the end of this chapter, you will be able to: Use Character Manipulating Functions Use Number Manipulating Functions Use Date Manipulating Functions Convert One datatype to another Work with NULL values © SQL Star International Ltd. 130
  • 134. Introduction So far you have retrieved, restricted and sorted data from the database. But, the real importance of the data lies in the way it is presented to the user. This requires formatting the data. To format data values stored in the database, SQL provides functions. Functions make your query more powerful. Function Capabilities Functions are an important and powerful feature of SQL that enables database users to format the values stored in the tables. The following tasks are achieved using functions:  Performing calculations on data values  Modifying the presentation format of data values  Formatting groups of rows to give a single output  Converting datatypes such as character(CHAR) to date(DATE) SQL Function Types SQL functions are of two types:  Single-row functions: These functions format only single rows and return one result for each row.  Multiple-row (or group) functions: These functions operate on groups of rows and return one result for each group of rows. Single-row Functions Single-row functions operate on single rows returning one value for every row fetched by the query. Single-row functions can be used in SELECT, WHERE and ORDER BY clauses. The syntax for issuing single-row functions is: <function_name> (column | expr [, arg1, arg2, …]) Where, function_name is the name of the function. column is the database column name. expr is any literal character string or calculated expression. arg1, arg2 are arguments passed into the function. Arguments mean:  Any constant or variable value  Any column name or expression A function may accept one or more arguments. However, the data value it returns may be of a different datatype than what it was when referenced. For instance, a function may accept an argument of character datatype but return a data value of number datatype. Single-row functions are of different types. They are as follows: © SQL Star International Ltd. 131
  • 135.  Character functions  Number functions  Date functions  Conversion functions  General functions Character Functions Character functions format character data values by accepting them as inputs and returning either character or number values as output. Character functions are further divided into two categories, case conversion functions and character manipulation functions. Case Conversion Functions These functions convert the case of the character data depending on the requirement. The following are the case conversion functions: Look at the following SELECT statement to identify the output derived using conversion functions: SELECT UPPER(cFirstName)|| ‗enrolled as member on ‘||dMembershipDt ―Member Details‖ FROM Member; The query result is as follows: © SQL Star International Ltd. 132
  • 136. ----------------- 21 rows selected. The usage of conversion functions is widely felt in the WHERE clause. For example, the following SELECT statement is issued to retrieve books written by John Grisham: SELECT cBookName FROM Book WHERE cAuthorName = ‗JOHN GRISHAM‘; The above query displays the following message: no rows selected. You will notice that this statement does not return any rows because the WHERE clause mentions the author name as ‗JOHN GRISHAM‘. But in the Book table all author names and book names are not stored in upper case, therefore, the name ‗JOHN GRISHAM‘ does not find an exact match in the table. This could be overcome using case conversion function as follows: SELECT cBookName FROM Book WHERE UPPER(cAuthorName) = ‗JOHN GRISHAM‘; Character Manipulation Functions These functions manipulate character data and return either character data or number data. Following are the character manipulation functions: Function Functionality CONCAT(column1| expr1, Joins the first argument (character value) column2| expr2) to the second. It is the same as the concatenation operator (||) except that you are limited to using only two arguments. © SQL Star International Ltd. 133
  • 137. E.g. CONCAT(‗Break‘, ‗fast‘) - Breakfast SUBSTR(column| expr, m, [n]) Extracts characters (from the character value) of n character length starting from the character position m. In case you omit n, it extracts the characters till the end of the string. E.g. SUBSTR(‗Function‘,1,3) - Fun SUBSTR(‗Star‘,2) – tar Incase, m is negative it starts the count from the end of the character value. E.g. SUBSTR(‗Stars‘,-1) – s LENGTH(column| expr) It returns the length of the character value. The result is a numeric value. E.g. LENGTH(‗Sqlstar‘)–7 INSTR(column| expr, m) It returns the numeric position of character m in the character string. E.g. INSTR(‗Sqlstar‘, ‗t‘) – 5 LPAD or RPAD(column| expr, n, It pads character values left justified or ‗string‘) right justified using string to n character position width E.g. LPAD(8000,10, ‗*‘)- ******8000 RPAD(‗8000‘,10, ‗*‘) – 8000****** TRIM(leading| trailing |both FROM It trims leading or trailing characters or trim_source) both from source text. In the e.g. it trims the leading ‗F‘ in the start of the character string ‗FIT‘ E.g. TRIM (‗F‘ FROM ‗FIT‘) – IT. REPLACE(text,search_string, character Replaces the specified text expression replacement_string) found in a string with the specified replacement string. E.g. REPLACE(‗SQLsTAR,‘s‘,‘S‘)- SQLSTAR TRANSLATE(string1, string_to_replace, Replace the 1st character in the replacement_string) string_to_replace with the 1st character in the replacement_string. E.g. TRANSLATE(‗SQLSTAR,‘STR‘, ‗3it‘)- 3QL3iAt Display the first and last names as a single name of members whose first name starts with ‗A‘. Display the length of the cFirstName column and find out the numeric position of the vowel ‗e‘ in the first name. Issue the following SELECT statement to see the output derived: SELECT CONCAT(cFirstName,cLastName) ―Name with A‖, LENGTH(cFirstName) Len, INSTR(cFirstName, ‗e‘) Instr FROM Member WHERE SUBSTR(cFirstName,1, 1) = ‗A‘; The query result is as follows: © SQL Star International Ltd. 134
  • 138. This statement displays following data for those members whose first names start with A:  Members first name joined with their last names  The length of their first names  The numeric position of the alphabet ‗e‘ in their first names. Number Functions Number functions accept number values as input and return only numeric values as output. Following are the types of number functions: © SQL Star International Ltd. 135
  • 139. To understand the usage of NUMBER functions, use the examples mentioned above in SELECT statements from the DUAL table. SELECT ROUND (67.238,2) ROUND,TRUNC (67.238,2) TRUNC FROM DUAL; SELECT CEIL(67.8)CEIL,FLOOR(67.8) FLOOR FROM DUAL; Date Functions In the Oracle database, dates are stored in an internal numeric format, which represents the century, year, month, day, hours, minutes and seconds. The default display for any date is DD-MON-RR. For example, the membership date of the member Austin is displayed as 12-OCT-90. However, the date is not stored in the database in this format. There is also time and century information associated with it. The complete date might be October 12th, 1990 10:30:55 a.m. Date functions accept date values and return a date or number datatype value. Following are the date functions: © SQL Star International Ltd. 136
  • 140. In addition to the functions mentioned above, you have the ROUND and TRUNC number functions, which can be used with dates too. ROUND (date, ‗fmt‘) – it rounds the date to the format model specified (month or year). It rounds the date to the nearest day if the format is omitted. Given below are some examples: ROUND (‘16-FEB-99’, ‘MONTH’) ->01-MAR-99 ROUND (‘16-FEB-99’, ‘YEAR’) ->01-JAN-99 Syntax for the TRUNC function is: TRUNC (date, ‗fmt‘) Examples for the same are: TRUNC (‗16-FEB-99‘, ‗MONTH‘) ->01-FEB-99 TRUNC (‗16-FEB-99‘, ‗YEAR‘) ->01-JAN-99 After having understood the functionality of the various DATE functions, look at their usage in the SELECT statement that follows. Suppose the New Jersey Central Library management requests a complete report, displaying the following details of all those persons who have been the members of the library for greater than a year:  Number of months the person has been the member of the library and  Number of months after which his/her membership is to be renewed SELECT cMemberID,dMembershipDt ―Date‖, © SQL Star International Ltd. 137
  • 141. MONTHS_BETWEEN(SYSDATE, dMembershipDt) ―Membership Period‖, ADD_MONTHS(dMembershipDt, 24) ―Renew Date‖ FROM Member WHERE MONTHS_BETWEEN(SYSDATE, dMembershipDt)>12; On issuing the query on member table, the following result is displayed: ------------------------------------- 21 rows selected SYSTIMESTAMP: SYSTIMESTAMP returns the system date, including fractional seconds and time zone of the system on which the database resides. The return type is TIMESTAMP WITH TIME ZONE. The following example returns the system date. SELECT SYSTIMESTAMP FROM DUAL; SYSTIMESTAMP ----------------- 28-MAR-00 12.38.55.538741 PM -08:00 Performing Arithmetic Operations with Dates Oracle stores dates as numbers in the database, therefore arithmetic operations performed with dates produce the following results: © SQL Star International Ltd. 138
  • 142.  Adding a number to or subtracting a number from a date results in a date value. For example, SELECT (SYSDATE+ 2) FROM DUAL;  Subtracting two dates results in the number of days between them. For example, subtracting the current date from the membership date, returns the number of days for which a person has been the member of the library. SELECT ROUND(SYSDATE-dMembershipDt) ―No of days‖, cMemberID FROM Member; The result of the statement is: ------------------------- 21 rows selected. Conversion Functions In an Oracle database, in addition to Oracle datatypes, other datatypes can also be defined. In such a case, the Oracle server automatically converts them to Oracle datatypes. Similarly, the Oracle Server can convert one Oracle datatype to another Oracle datatype. These datatype conversions are of two types: implicit conversion by the Oracle server or explicit conversion by the user. Implicit Datatype Conversion While assigning values to a column, the assignment succeeds only when the Oracle server converts the datatype of the value being assigned to that of the assignment target. For example, the nAge column of the Member table is of NUMBER datatype. However, while assigning values to it, if you enter the age of a person in quotes (‗24‘) it indicates that the value assigned is of CHARACTER datatype. In such a case the Oracle server implicitly converts it to NUMBER datatype. The Oracle server can automatically convert the following for assignments: © SQL Star International Ltd. 139
  • 143. While evaluating expressions in the WHERE clause, the Oracle Server can automatically convert CHARACTER values to NUMBER values provided the character string represents a number. For example, in the following statement the Oracle Server automatically converts the number of copies entered in the WHERE clause to NUMBER datatype and displays the desired result: SELECT cBookName FROM Book WHERE nNoOfCopies = ‗9‘; ----------- 9 rows selected. Similarly, for expression evaluation, the Oracle Server automatically converts CHARACTER value to DATE value provided the character string has the default date format. You have witnessed this implicit conversion in a number of SELECT statements written earlier. For example, SELECT cFirstName,cLastName FROM Member WHERE dMembershipDt = ‘19-SEP-00'; Explicit Datatype Conversion Datatype conversions can also be performed by the database developers or users, for which SQL has provided the following three functions: © SQL Star International Ltd. 140
  • 144. TO_CHAR Function The TO_CHAR function is used to explicitly convert number and date datatype values into character types. It converts NUMBER and DATE types to VARCHAR2. The uses of TO_CHAR function are as follows:  To display a number value as a character. The syntax for using the function with numbers is: TO_CHAR (number, ‗fmt‘) The syntax converts number values to character values using the format fmt specified. The number formatting models are: To understand the usage of the different number formats, look at the statement that follows. The amount entered into the nFine column of the Transaction table is all of number datatypes. But when you want to print a report displaying the amount the library earns by way of fine, it would be more appropriate to prefix the amount with a dollar symbol. This would require you to convert the values of the nFine column to character datatype. © SQL Star International Ltd. 141
  • 145. SELECT cTranID,dIssueDt, TO_CHAR(nFine, ‗$9999‘)Fine FROM Transaction WHERE nFine IS NOT NULL; The query displays the following result: ------------------ 19 rows selected. Points to remember while using TO_CHAR function with numbers:  If the number of digits exceeds that provided in the format model, then pound signs (#) are displayed in its place.  The decimal values are rounded to the number of decimal spaces provided in the format model. To convert date from the default format of DD-MON-YY to the format you specify. The syntax for using TO_CHAR function with dates is: TO_CHAR (date, ‘fmt’) This syntax converts the DATE data to the format fmt specified. The date format models are: Format Description CC or SCC Century. Using S places a minus sign before BC BC or AD BC/AD indicator B.C. or BC/AD indicator with periods A.D. YEAR or Year spelled out. For example, the year 2001 spelled as TWO THOUSAND SYEAR ONE YYYY or Year complete with all the four digits => 2001 SYYYY YYY or YY The last three, two, or one digits of the year => 001, 01,1 or Y Q Quarter of year – January through March=>1 MONTH Name of the month with blanks to pad a length of nine characters => DECEMBER MON Three letter abbreviation of the month name =>DEC for DECEMBER MM Month as a two digit value – 12 represents the month DECEMBER RM Month as a roman numeral WW Week of year (numeric representation) W Week of month DAY Name of the day (Friday) with blanks to pad a length of nine characters DDD Day of the year – 001 stands for Jan 1, 032 for Feb 1 DD or D Day of the month (01-31) and day of the week (1-7) DY Three letter abbreviation of the name of the day – Fri, Sat © SQL Star International Ltd. 142
  • 146. J Julian day stands for the number of days since 31 December 4713 BC TH Placed after any day of the months and are called ordinal number.E.g. for 4TH write DDTH SP It is used to spell out a day and is called spelled-out number E.g: for Four- Write SPDD SPTH Spelled-out ordinal number. E.g for Fourth write DDSPTH AM or PM Meridian indicator A.M. or Meridian indicator with periods P.M. HH or Hour of the day, or hour (1-12) or (0-23) HH12 or HH24 MI Minute (0-59) SS Second (0-59) Following guidelines need to be followed while using TO_CHAR with dates:  You need to enclose the format model in single quotation marks.  Format models are case sensitive.  Any of the valid date formats can be included as the format model.  Use a comma to separate the date value from the format model.  The output is padded with blanks. Use the fm (fill mode) element to remove the padded blanks.  By default the resultant column width is 80 characters. On issuing a SELECT statement to retrieve the membership dates of members, the dates are retrieved in the default date format. To convert it use the TO_CHAR function as follows: SELECT cFirstName||cLastName NAME, TO_CHAR(dMembershipDt, ‗fmDdSPTH ―of‖ Mon YYYY‘) ―Membership Date‖ FROM Member; The query displays the following result set: ----------------- 21 rows selected. The result displays the membership date as the format model specified. Notice that the day is spelled with the first letter capitalized and rest in lower cases, the month displayed as a three-letter abbreviation with the first letter capitalized, and the year displayed complete with four digits. © SQL Star International Ltd. 143
  • 147. In addition to the above mentioned date formats, there is a RR format. The RR format is explained below. The RR date format is similar to the YY format except that the century of the return date varies according to the specified two-digit year and the last two digits of the current year. Therefore, RR format allows you to specify different centuries. The following table illustrates the way the RR element behaves: Suppose you enter your date of birth as 20-JAN-79 (where the year of birth is 1979), then Oracle interprets it as 20th Jan 2079 (according to YY format). This is incorrect. However, with the RR format, it will be interpreted as: TO_NUMBER and TO_DATE Functions To convert a character string to a number or a date you need to use TO_NUMBER and TO_DATE function. For conversion use the format models previously explained. To convert a character string to number or date, the following syntax is used: TO_NUMBER (char, ‗fmt‘) TO_DATE (char, ‗fmt‘) © SQL Star International Ltd. 144
  • 148. Suppose the user querying the Member table is unaware of the default date format, then while retrieving the IDs of members enrolled on 13 th March 1989, he/she would issue the following SELECT statement: SELECT cMemberID FROM Member WHERE dMembershipDt = ‗March 13,1989‘; And encounter the following error message: ERROR at line 3: ORA-01861: literal does not match format string This SELECT statement is erroneous because the date entered in the WHERE clause is not in its default format. This can be rectified using the TO_DATE function as follows: SELECT cMemberID FROM Member WHERE dMembershipDt = TO_DATE (‗March 13,1989‘, ‗Month dd,YYYY‘); The result is now correct as given below: General Functions General functions work with any datatype and comprise of the following:  NVL function  NVL2 function  DECODE function  The CASE expression, which comprises: • Simple CASE expression • Searched CASE expression • NULLIF • COALESCE NVL Function Performing calculations with null values result in null values. This situation can be overcome using the NVL function. NVL function converts a null value to a specified value. This function can be used with any datatype be it character, number, or date. Its syntax is: © SQL Star International Ltd. 145
  • 149. NVL (expr1, expr2) Where, expr1 is the column containing null value expr2 is the value for converting the null value The datatypes of both expr1 and expr2 must match. While issuing a SELECT statement to retrieve details of members, some of the values of the cPhone and cEmailID columns may be null. Rather than leaving them as null, you can use the NVL function to display a suitable text in place of the null value. SELECT cMemberID,NVL(cPhone,‘not known‘)Phone FROM Member; On executing this statement, the text ‗not known‘ would be displayed for all those members whose phone numbers are unknown. --------------- 21 rows selected. NVL2 Function The NVL2 function returns the result based on its examining the first expression. If the first expression is not null, the function returns the second expression. If the first expression is null, the function returns the third expression. The syntax of NVL2 function is as follows: NVL2 (expr1, expr2, expr3) Where, expr1 is the expression that may or may not contain null expr2 is the expression returned in case expr1 is not null expr3 is the expression returned in case expr1 is null While retrieving transaction details of members, their fine status could be made more descriptive, such that if fine is null, the text ―No fine dues‖ is displayed, and if fine is not null, the text ―Defaulter – fine due‖ is displayed. To achieve this, the following SELECT statement is to be written: SELECT cMemberID, dIssueDt, dActualReturnDt, nFine, NVL2(nFine,‘Defaulter - Fine due‘, ‗No fine due‘) ―Fine Status‖ FROM Transaction; The result of the query is: © SQL Star International Ltd. 146
  • 150. ---------------- 31 rows selected. DECODE Function The functionality of DECODE is similar to that of IF-THEN-ELSE logic used in most of the programming languages. Its syntax is: DECODE (column / expr, search1, result1 [, search2, result2,…,] [, default]) The DECODE function compares the expr or the column values to each of the search values and returns the result if the expr is same as the search value. If we omit the default value, it returns a null value wherever the expr does not match the search value. Suppose the library increases the stock of books, but by different quantities for its branches, the same could be illustrated using the DECODE function as follows: SELECT cBranchID, nNoOfCopies, DECODE (cBranchID, ‘01ADLNJ‘, nNoOfCopies+1, ‘02CHSNJ‘,nNoOfCopies+2, nNoOfCopies) ―revised copies‖ FROM Book WHERE cBranchID IN (‘01ADLNJ‘,‘02CHSNJ‘); The result of the query is. ---------------- © SQL Star International Ltd. 147
  • 151. 70 rows selected. In the statement, the cBranchID value has been decoded, that is,  If branch ID is 01ADLNJ, the number of copies is increased by 1  If branch ID is 02CHSNJ, the number of copies is increased by 2  In case of all other branches the number of copies is to remain the same. The CASE Expression CASE expressions use IF-THEN-ELSE logic in SQL thereby facilitating conditional inquiries. The SQL: 1999 standard has the following four types of CASE expressions:  Simple CASE expression  Searched CASE expression  NULLIF  COALESCE Simple CASE Expression The simple CASE expression is similar to the DECODE function. It does not support comparison operators. Its syntax is as follows: CASE expr WHEN comparison_expr1 THEN return_expr1 WHEN comparison_expr2 THEN return_expr2 WHEN comparison_exprn THEN return_exprn ELSE else_expr END The CASE expression functions as follows: The Oracle server searches for the first WHEN…THEN pair for which expr is equal to comparison_expr, and returns return_expr. In case none of the WHEN…THEN pairs meet this condition, and if an ELSE clause exists, then Oracle server returns the else_expr, otherwise it returns null. [The literal NULL cannot be specified for all return_exprs and else_exprs, and all the expressions must be of the same datatype] The Library management decides to revise the member fee structure as follows: If grade is ‗A‘ then increase the fee by 5% If grade is ‗B‘ then increase the fee by 10% If grade is ‗C‘ then increase the fee by 15% For all other grades there is no increase in fee The effect of implementing the above changes could be viewed by writing the following SELECT statement making use of the CASE expression: SELECT cGrade,nFeeAmount, CASE cGrade WHEN ‗A‘ THEN nFeeAmount*1.05 WHEN ‗B‘ THEN nFeeAmount*1.10 WHEN ‗C‘ THEN nFeeAmount*1.15 © SQL Star International Ltd. 148
  • 152. ELSE nFeeAmount END ―Revised Fee‖ FROM MemberFee; The result of the query is: Searched CASE Expression Searched CASE expression can conditionally be used to search and replace values within expressions. Comparison operators can be used in the conditional expression. Searched CASE expressions are more flexible than simple CASE expressions because, within searched CASE expressions, each WHEN condition can be different and multiple conditions can be combined with logical operators. For example, look at the following query: SELECT cBookName,cCategoryID,nNoOfCopies, CASE WHEN cCategoryID LIKE ‗__%FIC‘ THEN nNoOfCopies+2 WHEN cCategoryID LIKE ‗__%ROM‘ THEN nNoOfCopies+1 WHEN cCategoryID LIKE ‗__%NFI‘ THEN nNoOfCopies+3 WHEN cCategoryID LIKE ‗__%SFI‘ THEN nNoOfCopies+4 WHEN cCategoryID LIKE ‗__%MYS‘ THEN nNoOfCopies+1 ELSE nNoOfCopies END ―Revised Copies‖ FROM Book WHERE cBranchID=‘03HAMNJ‘; In the query, you are trying to determine the revised number of copies of books based on the book categories for branch ‗03HAMN‘ as follows:  If category is ‗FIC‘ then increase copies by 2  If category is ‗ROM‘ then increase copies by 1  If category is ‗NFI‘ then increase copies by 3  If category is ‗SFI‘ then increase copies by 4  If category is ‗MYS‘ then increase copies by 1  For all other categories there is no increase in the number of copies The query generates the following result: © SQL Star International Ltd. 149
  • 153. ---------------- 39 rows selected. NULLIF Function The NULLIF function compares two expressions. If the first expression is equal to the second, the function returns NULL. If they are not equal, the function returns the first expression. The syntax of NULLIF is: NULLIF (expr1, expr2) Where, expr1 is the expression compared to expr2, and is the expression returned in case the two expressions are not equal. [The literal NULL cannot be specified for expr1] expr2 is the expression compared to expr1 The semantics of the NULLIF expression is defined as follows: CASE WHEN expr1=expr2 THEN NULL ELSE expr1 END The NULLIF function can be used while querying the Transaction table, in a way that by comparing the return dates with their actual return dates helps determine whether books were returned on the return date set or at a later date. SELECT cMemberID, dReturnDt, dActualReturnDt,NULLIF(dActualReturnDt,dReturnDt)‖Result‖ FROM Transaction; On executing the query, the following result is generated wherein, the result displays null if dReturnDt and dActualReturnDt are equal, and displays the actual return date if they are not equal: ----------------- © SQL Star International Ltd. 150
  • 154. 32 rows selected. COALESCE Function The COALESCE function is a generalization of the NVL function. However, its advantage over the NVL function is that it can take multiple alternate values. The COALESCE function accepts any number of expressions, and returns the first non-null expression in the list. If the first expression is not null, the function returns it, or else, it does a coalesce of the remaining expressions. The syntax of The COALESCE function is: COALESCE (expr1, expr2, …, exprn) Where, expr1 is returned if it is not null. expr2 is returned if expr1 is null and this expression is not null. exprn is returned if the preceding expressions are null. The semantics of the COALESCE expression is defined as follows:  When the expression has exactly two arguments CASE WHEN expr1 IS NOT NULL THEN expr1 ELSE expr2 END  When the expression has three or more arguments CASE WHEN expr1 IS NOT NULL THEN expr1 ELSE COALESCE (expr2, expr3,…,exprn) END The following query makes use of the COALESCE function: SELECT cTranID, dReturnDt, dActualReturnDt, COALESCE(dActualReturnDt,dReturnDt,sysdate) ―Returned‖ FROM Transaction; In the above SELECT statement, if the actual return date(DACTUALRETURNDT) is not null, it is returned. If the actual return date(DACTUALRETURNDT) is NULL, then the return date (DRETURNDT) is displayed provided it is not null. If both DACTUALRETURNDT and DRETURNDT are null, then SYSDATE is displayed as shown below. Summary In this chapter, you have learnt that:  Functions are built-in programs that accept arguments and return a value. © SQL Star International Ltd. 151
  • 155. Data in the database can be retrieved using SQL functions in a desired manner. These functions accept arguments of different data type such as character, data and number, returning a single output for each row. Hence they are known as Single Row functions.  While retrieving the character information, case of a character can be controlled  using Case Manipulation functions and specific information from these characters can be extracted using Character Manipulation functions.  Number functions can be used to work with number data which accept number values as input and return only numeric values as output.  Date Functions are used to work with Date data and returns number as well as date output.  In case of Incompatibility of data, conversion function such as TO_CHAR, TO_NUMBE and TO_DATE are used to explicitly convert data to specific datatypes. Implicit conversions are handled by Oracle server itself.   NULL values can be handled using a set of functions which are categorized under the general functions. Using these function one can improve the logic of the programs. Lab Exercise 1. Write a query to display:   The last name in uppercase   The length of the last names   Job IDs starting from the fourth character. The output should be as shown below. © SQL Star International Ltd. 152
  • 156. ---------------- 107 rows selected. 2. Write a query to display employee ID, first name, salary and salary increased by 10%, which is expressed as a whole number. Name the column as ‗New_Sal‘. 3. Write a query to display the first name and number of months worked by the employees. Round the number of months worked to the closest whole number. Sort the result by the number of months employed. The output should be as shown below. 4. Write a query to display the employee ID, hire date, and salary. The hire date should appear as (For E.g.) ‗Seventh of June 1994 12:00:00 AM‘. The salary should appear as $15,000. Give each column an appropriate label as shown below. 5. Write a query to display the employee ID, hire date and salary review date. The salary review date is the first Friday after a year of service. Name the column as ‗Salary Review Dt.‘. The salary review dates should appear as ‗Friday, 31 st of July, 2000‘. © SQL Star International Ltd. 153
  • 157. 6. Write a query to retrieve the last name and hire date of employees hired before 1994. The query should return the same result even if the query is run in 1994 or now. 7. Write a query to retrieve the employee ID, salary, commission, and annual salary, which is calculated by multiplying salary by 12, and then adding the commission percentage to the result. Annual salary is to be calculated for all employees irrespective of whether they earn a commission or not. The query result should be as shown below. 8. Write a query to retrieve the employee ID, job ID and salary of all employees. The query should calculate increase in salary on the following basis:  If job ID is ‗SA_REP‘, salary increase is 10%  If job ID is ‗ST_CLERK‘, salary increase is 15%  If job ID is ‗IT_PROG‘, salary increase is 20%  For all other job IDs, there is no salary increase. Perform the above query using CASE expression as well as DECODE function. © SQL Star International Ltd. 154
  • 158. Chapter 7 Working with Grouped Data Explain the various group functions Use of NULL value function Use of GROUP BY clause Use of HAVING clause © SQL Star International Ltd. 155
  • 159. Objectives At the end of this chapter, you will be able to: Use Group functions Use GROUP BY clause Restrict the groups using HAVING clause Introduction As we have seen earlier, SQL Functions are broadly categorized into two types, Single row functions and Multiple row functions. We are familiar with the working of single row function and its use. Let us now, look into the second category of the functions-Group functions. What are these group functions and why do we need them? To explain the above question, let me relate a scenario. Suppose an organization wants to calculate the total salary expenditure incurred for a particular month. Since, the calculation has to be done on a collective data, we need to use Group Functions. Further, if they need to know what is the salary disbursed in each department, the table has to be split into groups and then, the Group Functions need to be applied on it. So, Group Function performs data operations on sets (or groups) of rows. The set may be the whole table or table split into groups. It gives one result per group. Group functions differ from single row functions, in that, they can manipulate several rows at a time. This helps in obtaining summary details such as averages, sum, maximum or minimum. Group Functions There are different group functions available. Some of them are:  AVG  SUM  MAX  MIN  COUNT © SQL Star International Ltd. 156
  • 160. AVG Function This function returns the average value of columns with numeric values. Its syntax is: AVG ([distinct| all] x) It returns the average value of the values of column x, ignoring null values. Where, distinct is used in order to consider only non-duplicate values. all is the keyword that causes the function to consider even duplicate values. This is the default and hence, need not be mentioned. For example, to calculate the average fine amount earned by the library, the following statement is issued: SELECT AVG(nFine) FINE FROM Transaction; Output: FINE -------- 5.475 But this statement ignores null values and calculates the average fine by dividing the total fine amount by the number of people who have paid the fine. Therefore, use the NVL function to include null values. Now, notice the difference in the average fine amount. SELECT AVG(NVL(nFine, 0)) FINE FROM Transaction; Displays: FINE -------- 3.421875 SUM Function This function returns the total or sum of given values. Its syntax is: SUM ([distinct|all] x) Which returns the sum of all the values in column x, ignoring null values. For example, to calculate the total number of copies of books stored in branch ‗04RANNJ‗ the following SELECT statement is issued: SELECT SUM(nNoOfCopies) TOTAL FROM Book WHERE cBranchID = ‘04RANNJ‘; Displays: TOTAL -------- 165 MAX and MIN Functions These functions return the maximum and the minimum values respectively for any given expression. You can use these functions for any datatype unlike AVG and SUM. Their syntax is: © SQL Star International Ltd. 157
  • 161. MAX ([distinct|all] x) MIN ([distinct|all] x) Which returns the maximum and the minimum value for column x, ignoring null values. For example, in order to determine the senior most and junior most members of the library based on their age as well as on their membership dates, issue the following SELECT statement: SELECT MAX(nAge) Oldest, MAX(dMembershipDt) JuniorMem, MIN(nAge) Youngest, MIN(dMembershipDt) SeniorMem FROM Member; Displays: COUNT Function There are two formats for COUNT function. They are: COUNT (*) COUNT (column_name) COUNT (*) returns the total number of rows in a table including both the duplicate rows as well as those rows containing null values in any of the columns. In case a WHERE clause is included in the SELECT statement, the function returns the count of only those many rows that satisfy the WHERE condition. For example, to retrieve the total number of members whose age is above twenty, issue the following statement: SELECT COUNT (*) FROM Member WHERE nAge > 20; The query displays the following result: COUNT(*) ------- 10 Using of COUNT (*) is not recommended because the processing mechanism is very slow, as it has to first resolve all column names in the table. This step is unnecessary when you need to know only the number of rows in a table. Instead, use COUNT (1) or COUNT (ROWID). A ROWID is a pseudo-column. It is not a part of the table. Rather, they are unique numbers generated by the server to identify each row uniquely and they are stored internally within Oracle. COUNT (column_name) on the other hand, returns the number of rows in a table, but excludes rows with null values in the column identified by column_name. For example, to display the number of members who have paid fine for books issued on ‗08-AUG-2000‘, issue the following statement: SELECT COUNT (nFine) FROM Transaction WHERE dIssueDt = ‘08-AUG-2000'; Displays: © SQL Star International Ltd. 158
  • 162. COUNT(NFINE) -------- 2 The result gives a total of two rows (instead of three) because one of the members who had issued books on ‗08-AUG-2000‘ did not have to pay fine as they had returned the books on the due dates. Creating Logical Groups of Data Till now you have used group functions, which treat the entire table as one group. But, you may need to collect summarized details for different groups within the same table. For example, finding the total number of books stored in a library can be done using the COUNT function in a simple SELECT statement as shown below. SELECT COUNT (cBookName) FROM Book; Displays: COUNT(CBOOKNAME) --------------- 186 However, situations arise when you need to know the total number of books belonging to different categories. In such a situation you have to group the books based on the categories to which they belong. This is done using the GROUP BY clause. The GROUP BY clause divides the table into smaller groups. Its syntax is: SELECT column, group_function (column) FROM table [WHERE condition] [GROUP BY group_by_column] [ORDER BY column]; Where, column is the individual column you want to select. group_function (column) is the column on which a group function has been applied. Group_by_column specifies those columns whose values will form the basis for splitting the table into groups of rows. There are certain points to remember while using the GROUP BY clause: In order to select individual columns (columns that are not an aggregate function) along with the column specified within the group function, place the individual columns in the GROUP BY clause. For example, to retrieve the total number of books grouped according to their categories, if you type the following: SELECT cCategoryID, COUNT(cBookName) FROM Book; © SQL Star International Ltd. 159
  • 163. You get an error: ERROR at line 1: ORA-00937: not a single-group group function.  Use the WHERE clause before dividing rows into groups.  Column alias cannot be used in the GROUP BY clause.  Group functions can be used in the ORDER BY clause. The following SELECT statement explains how to retrieve the total number of books grouped according to their categories: SELECT cCategoryID, COUNT(cBookName) FROM Book GROUP BY cCategoryID; And the result is: ----------------------- 14 rows selected. In the above example, the SELECT clause contains the columns to be retrieved i.e. the book category IDs and the total number of books in each of the categories. The FROM clause contains the table that needs to be accessed i.e. the Book table. The GROUP BY clause specifies how the rows are to be grouped. The rows are grouped based on the category to which they belong. The same example could be rewritten as follows: SELECT COUNT(cBookName) FROM Book GROUP BY cCategoryID; In this statement, the column specified in the GROUP BY clause is not contained in the SELECT list, yet it displays the number of books belonging to different categories. This shows that the GROUP BY column need not be in the SELECT list. But the results do not look meaningful. So far we have grouped rows based on one column, but you may need to display results for groups within groups. For example, to find the total number of books published, each year grouped by category, you would first need to group the table by book category, and within that group, you would need to group by publishing year. SELECT cCategoryID,dPublishedYr Published, COUNT(cBookName)‖Total Books‖ FROM Book GROUP BY cCategoryID, dPublishedYr; The result of the query is: © SQL Star International Ltd. 160
  • 164. ------------------------------------ 45 rows selected. Restricting Grouped Data Suppose you are interested in finding the total number of books belonging to each category, but display only those categories, which have more than 10 books belonging to them. In such a case, you need to put restriction on the groups. SELECT cCategoryID, COUNT(cBookName) FROM Book WHERE COUNT(cBookName)>10 GROUP BY cCategoryID; This statement gives you an error at the following statement: WHERE COUNT (cBookName)>10 * Error at line 3 ORA-00934: group function is not allowed here This statement gives rise to the following error: ‗group function is not allowed here‘, indicating that you cannot use group functions in the WHERE clause. Instead you need to use the HAVING clause. By using the HAVING clause you specify the groups that need to be displayed. You can place the HAVING clause before the GROUP BY clause, but it is more logical to place the GROUP BY clause before because you first form the groups, then perform the group functions. SELECT cCategoryID,COUNT(cBookName)‖No. of Books‖ FROM Book GROUP BY cCategoryID HAVING COUNT(cBookName)>10; The result of the query is: © SQL Star International Ltd. 161
  • 165. ------------------ 10 rows selected. Summary In this chapter, you have learnt that: Group function takes a collective data for its operation and returns a single value. The function can act upon character, number and date datatypes respectively.  The functions discussed in this chapter are sum(), avg(), min() , max() and count(). NULL values are ignored in all these functions except count (*).  To get a group wise resultant, the table is split into groups using GROUP BY clause. Groups can be based on one or more columns.  In order to select individual columns (columns that are not an aggregate function) along with the column specified within the group function, place the individual columns in the GROUP BY clause.  Using WHILE clause, one can restrict the number of rows used in the formation of the group.  Using HAVING clause, one can restrict the groups to be included in the final resultant. © SQL Star International Ltd. 162
  • 166. Lab Exercise 1. Write a query to display the maximum, minimum, sum, and average salaries for each job type. The query result should be as shown below. 2. Write a query to display the number of employees belonging to the same department numbers. The query output should be as follows: 12 rows selected. 3. Write a query to display the manager ID and the highest paid employee for that manager. Exclude employees who do not have a manager. 4. Write a query to display the job ID and total salary for each job that has total salary exceeding $13000. © SQL Star International Ltd. 163
  • 167. Chapter 8 Joins Introduction to Joins Discuss the Need of Joins Types of Joins Oracle Proprietary Join SQL: 1999 syntax Join Three way Join with the ON clause Using Set operators © SQL Star International Ltd. 164
  • 168. Objectives At the end of this chapter, you will be able to:  Identify the need for joins Obtain data from multiple tables using Oracle proprietary syntax Obtain data from multiple tables using SQL:1999 syntax Use Set operators © SQL Star International Ltd. 165
  • 169. Introduction to Joins Organizations usually have large databases consisting of many tables. It is not functionally efficient to have a single table storing all data. In the process of their business, organizations require to prepare reports by extracting data that may be from one or more than one table. You can retrieve data from more than one table by creating joins. Joins are query statements made on more than one table using a column, which is common to both tables. Retrieving Data from Multiple Tables View the report shown below to understand the use of a join: The report displays names of books and their publishers. The book names are derived from the Book table, where as the publisher names are derived from the PublisherDetails table. In order to join these two tables there must exist a relationship between them. For instance, Book and PublisherDetails tables in the library database are related through the column cPublisherID. You can query for the names of the books and their publishers with a join as this column relates the two tables. The syntax for creating a join is: SELECT table1.column, table2.column… FROM table1, table2 WHERE table1.column1= table2.column2; OR SELECT t1.column, t2.column… FROM table1 t1, table2 t2 WHERE t1.column1= t2.column2; Where, SELECT table1.column, table2.column… © SQL Star International Ltd. 166
  • 170. lists the columns that you want to be displayed along with any of the functions or column alias. FROM table1, table2 specifies the table where the data is stored. WHERE table1.column1= table2.column2 specifies the condition that needs to be met for the join to be created. In a table join, the FROM clause contains two or more tables which are the source for data. The WHERE clause contains comparison operations, which specify how data from the tables are to be joined. Guidelines for writing Join conditions  The FROM clause contains names of more than one table each followed by an alias. This reveals an interesting aspect of Oracle. Not only the columns in the SELECT statement can have alias, but even the tables in the FROM clause can have aliases.  Table alias must not be more than 30 characters in length.  The table alias given for a table in the FROM clause must be used for the table name throughout the SELECT statement.  The table alias is valid only for the current SELECT statement.  Columns having common values in multiple tables may have the same column names. For instance, the column-containing publisher Ids has the name cPublisherID in both, the Book as well as the PublisherDetails table. This makes it easier to identify them as columns with similar data. However, this causes ambiguity as the Oracle SQL processing mechanism is unable to resolve the column names (from which table is the column being referred to) and therefore, would return an error. To avoid ambiguity, precede each column with the table name or the alias.  You need not precede a column name with its table name or alias if it appears only in one of the tables specified in the FROM clause. But, by prefixing the table name or alias you would be able to enhance database access, as the server would know exactly, in which table the column resides.  For joining n tables, you must have at least (n-1) join conditions. For instance, to join three tables there must be a minimum of two join conditions. What is a Cartesian product? A Cartesian product results in the display of a large number of rows, that is, all combination of rows, where all rows in the first table are joined to all the rows in the second table. A cartesian product is generated as a result of:  Omitting a join condition  Specifying an invalid join condition The following example illustrates how a Cartesian product gets generated: SELECT cMemberID, nFeeAmount FROM Member,MemberFee; The statement displays the following output: © SQL Star International Ltd. 167
  • 171. ---------------- 84 rows selected. The Member IDs and their fee amounts are displayed from the Member table and the MemberFee table respectively. But since the WHERE clause has been excluded, all rows from the Member table are joined with all the rows in the MemberFee table returning 84 rows in the result. In order to avoid a Cartesian product ensure that you have at least n-1 join conditions in the SELECT statement for n joined tables. There must be one join condition to avoid the Cartesian product. Types of Joins Tables are joined by including a join condition in the WHERE clause. There are different ways of joining data. The types of joins are:  Oracle Proprietary Joins  Equijoin  Non-Equijoin  Outer join  Self join  SQL:1999 Compliant Joins  Cross joins  Natural joins  Using clause  Full or two sided upper joins  Arbitrary join conditions for outer Joins © SQL Star International Ltd. 168
  • 172. Obtaining Data from Multiple Tables Prior to Oracle9i, you could obtain data from multiple tables using the ‗join‘ statement, which belongs to Oracle proprietary syntax. These ‗join‘ statements include equijoin, non-equijoin, outer join and self join. Creating Equijoins Equijoins are also referred to as simple joins or inner joins. In an equijoin we make use of the equality operator in the join condition. It returns data where column values in one table equal that of the other table. For example, in order to display the publisher‘s name for each book, you would have to compare the publisher ID values in the Book table with the publisher ID values in the Publisher table. There exists an equijoin relationship between the Book table and the Publisher table, as the values in the cPublisherID columns of both the tables are the same. This is executed with: SELECT B.cBookName, B.cPublisherID, P.cPublisherName FROM Book B, PublisherDetails P WHERE B.cPublisherID = P.cPublisherID; Which displays the following result: ------------------- 184 rows selected. In the statement the SELECT clause retrieves book names and their publisher‘s ID from the Book table and publisher names from the PublisherDetails table. These tables are joined by the equijoin condition specified in the WHERE clause. Additional Search Condition The above example retrieved the publisher names of all the books stored in the library by issuing a join condition in the WHERE clause. However, in addition to the join, you may want some other restrictive condition to be specified in the WHERE clause. For instance, retrieve the publisher names of the books written by ‗John Grisham‘ and which are stored in the ‗Chester‘ branch of the library. You can specify this additional criteria in the WHERE clause using the AND operator as follows: SELECT B.cBookName, B.cPublisherID, P.cPublisherName FROM Book B, PublisherDetails P WHERE B.cPublisherID = P.cPublisherID AND B.cAuthorName = ‗John Grisham‘ AND B.cBranchID = ‘02CHSNJ‘; The result of the query is: © SQL Star International Ltd. 169
  • 173. So far you have joined only two tables, but it is also possible to join more than two tables when the need arises. For example, if the desk officer wants to display the category name and the publisher name of books written by ‗Nora Roberts‘ stored in branch ‗05PRINJ‘, you would have to join three tables, namely the Book table, the PublisherDetails table and the Category table as follows: SELECT B.cBookName, C.cCategoryName, P.cPublisherName FROM Book B, Category C, PublisherDetails P WHERE B.cCategoryID = C.cCategoryID AND B.cPublisherID = P.cPublisherID AND B.cAuthorName = ‗Nora Roberts‘ AND B.cBranchID = ‘05PRINJ‘; The result of the query is: Creating Non-Equijoins A non-equijoin relationship is established when a column in a table does not directly correspond to any column in the other table. To establish a non-equijoin relationship you need to use operators other than equal (=), such as <=, >=, or BETWEEN. For instance, based on the age of a person the library charges the membership fee. The MemberFee table contains details about the amount of fee payable by people falling within the range of ages specified. To display the different membership fee amounts, age must be specified between a range as shown below. SELECT M.cMemberID, M.cFirstName, M.dMembershipDt,M.nAge,MF.nFeeAmount FROM Member M, MemberFee MF WHERE M.nAge BETWEEN MF.nLowerAge AND MF.nUpperAge; The query displays the following result: ------------ 21 rows selected. © SQL Star International Ltd. 170
  • 174. Creating Outer Joins An outer join is used to retrieve data from multiple tables where information in one of the joining columns is deficient compared to the same in the other tables. For instance, querying the Book table will not display the list of books that have been issued and those that have not, because the result of the query will not specify which books have been borrowed. To identify which books have been issued and which can be issued, you need to use an outer join. The outer join operator is a plus sign enclosed in parentheses (+). You can place the operator on either side of the WHERE clause condition, which ever is deficient in data. That is, place it after the column, which does not have values that match corresponding values in the other table. It denotes the creation of one or more null rows in the deficient table that can be joined to the non-null rows of the non- deficient table. But an outer join operator can appear only on one side of the condition. The syntax to create an outer join is: SELECT table1.column, table2.column FROM table1, table2 WHERE table1.column (+) = table2.column [WHERE table1.column = table2.column (+)]; The situation mentioned above can be handled in the following way: SELECT T.cMemberID,B.cBookName FROM Book B, Transaction T WHERE B.cBookID = T.cBookID (+); The result of the query is: ----------------- 186 rows selected. From the output, you can identify all those books that have been issued by the member ID, mentioned along with it. The books that are available but have never been borrowed have no match in the transaction table and hence there is no member ID mentioned along with it. Creating Self Joins A self-join is a join that is created while joining a table to itself. A self-join can be created with a single table only. You can create a self-join when you want two kinds of information from the same table or, in other words, you want the same data but from two different angles. This can best be explained by the following example: In order to find the names of the superiors of each of the library staff members, you would have to join the LibStaff table to itself. The information contained in the LibStaff table is as follows: © SQL Star International Ltd. 171
  • 175. 7 rows selected. From the details displayed in the LibStaff table, to find the immediate superior of ‗Matt Scummen‘, you would have to: Identify ‗Matt Scummen‘ from the cLibStaffName column. Identify the manager (or superior‘s) number for ‗Matt Scummen‘ from the nLibMgrNo column. On identifying, you get the manager number as 104. Identify the name of the superior having staff number as 104 from the cLibStaffName column. The staff member having staff number as 104 is ‗Susan Dudley‘. Therefore, ‗Susan Dudley‘ is ‗Matt Scummen‘s‘ superior. To identify ‗Matt Scummen‘s‘ superior, you had to look at the LibStaff table twice. First, to locate ‗Matt Scummen‘ and his superior‘s staff number. Second, to locate the name of the superior having the staff number 104. Rather than doing this manually, you could derive at the following result using self join: Subordinates and Their Superiors To join LibStaff table to itself, you would have to issue the following SELECT statement: SELECT Subordinate.nLibStaffNo, Subordinate.cLibStaffName, Subordinate.nLibMgrNo, Superior.nLibStaffNo, Superior.cLibStaffName FROM LibStaff Subordinate,LibStaff Superior WHERE Subordinate.nLibMgrNo=Superior.nLibStaffNo; In the above self join, LibStaff table has been assigned two aliases, Subordinate and Superior in the FROM clause. The join condition in the WHERE clause matches the subordinates manager number with the staff number of the superior. The result of the self-join is: © SQL Star International Ltd. 172
  • 176. Obtaining Data from Multiple Tables using SQL: 1999 Syntax Prior to Oracle9i, the Oracle database supported joins using the proprietary syntax. The traditional join syntax has its limitations. In a complex query, it can be difficult to parse the WHERE clause to separate the join condition from other restrictions placed on the query results. In addition, the programmers sometimes overlook to specify any join condition at all, leading to Cartesian product. Support for SQL/99 standard join syntax was introduced in Oracle 9i.This support makes it easier to write portable applications and enables full outer joins. Types of SQL: 1999 Joins To retrieve data from more than one table, you make use of the ‗join‘ statement. The SQL: 1999 join syntax provides the following types of joins:  CROSS JOIN  NATURAL JOIN  The INNER/OUTER JOIN  FULL OUTER JOIN The SQL: 1999 join syntax is as follows: SELECT table1.column, table2.column FROM table1 [CROSS JOIN table2] | [NATURAL JOIN table2] | [JOIN table2 USING (column_name)] | [JOIN table2 ON (table1.column_name = table2.column_name)] | [LEFT|RIGHT|FULL OUTER JOIN table2 ON table1.column_name = table2.column_name)]; Where, table1.column is the table and column from which the data will be retrieved. CROSS JOIN retrieves a Cartesian product from the two tables. © SQL Star International Ltd. 173
  • 177. NATURAL JOIN joins two tables, based on the same column name. JOIN table USING column_name – performs an equijoin based on the column name. JOIN table ON (table1.column_name = table2.column_name). performs an equijoin based on the condition in the ON clause. Cross Joins The CROSS JOIN clause is used to retrieve the Cartesian product of two tables, which is the cross product of two tables. For example, SELECT cBookName, cCategoryName FROM Book CROSS JOIN Category; The CROSS JOIN statement retrieves the names of books and categories from the Book and Category tables. The keyword CROSS JOIN indicates that a Cartesian product must be retrieved. Natural Joins A NATURAL JOIN takes into account all the columns in the two tables that have the same name and the same datatype. In prior releases, to join two tables, you had to explicitly specify the columns on which the JOIN was to be based. However, in case of NATURAL JOINS you need not specify the column names explicitly. A natural join is performed automatically based on all the columns in two tables that have same name and same datatype. If you perform a natural join on two tables that have columns with same names but different datatypes, a NATURAL JOIN syntax error is returned. When you perform a natural join on two tables, it selects rows that have equal values in all the matched columns. The keyword NATURAL JOIN is used to perform this type of join. SELECT cTranID, dIssueDt, cBookName, dActualReturnDt FROM Book NATURAL JOIN Transaction; In the statement, Transaction table is joined to the Book table taking into account cBookID column, which exists in both the tables. Had there been more common columns, NATURAL JOIN would have used them. The same result can be obtained using equijoin as follows: SELECT cTranID, dIssueDt, cBookName,dActualReturnDt FROM Book b, Transaction t WHERE b.cBookID = t.cBookID; A Natural Join with WHERE clause You can also use WHERE clause with a NATURAL JOIN to restrict the result of your query. SELECT cTranID, dIssueDt, cBookName, dActualReturnDt FROM Book NATURAL JOIN Transaction WHERE cBookID IN (‗SFI050001993‘,‗NFI040000224‘, ‗HUM050001003‘); In the statement a natural join is created on Book and Transaction tables. The WHERE clause restricts the output of the query. © SQL Star International Ltd. 174
  • 178. The USING Clause Natural joins can be created on tables having columns with same name and same datatype. However, if tables have columns with same name but different datatype, the USING clause can be used. The NATURAL JOIN and USING clauses are mutually exclusive. The USING clause is used to specify the columns to be used for equijoins. Although more than one column may match in two tables, the USING clause can be used to match only one column. The following statement shows the usage of the USING clause: SELECT t.cTranID, t.dIssueDt, b.cBookID, b.cBookName,t.dActualReturnDt FROM Book b JOIN Transaction t USING (cBookId) WHERE cBookID in (‗SFI050001993‘, ‗NFI040000224‘, ‗HUM050001003‘); The USING clause with WHERE Clause Use the USING clause with the WHERE clause to restrict records retrieved from two tables. First, join the tables and then use the USING clause as follows: SELECT t.cTranID, t.dIssueDt, cBookID, b.cBookName, t. dActualReturnDt FROM Book b JOIN Transaction t USING (cBookID) WHERE cBookID = ‗FIC030001111‘; In the above statement, first, the Book and the Transaction tables are joined with the JOIN keyword using the cBookID column to match the columns. The search is restricted to condition specified in the WHERE clause. The ON Clause A natural join is based on all columns with same name, same datatype, and same values. You can use the WHERE clause to retrieve the records based on some condition. You can also specify a condition in the natural joins using the ON clause. The ON clause specifies a condition that is separate from search condition specified by the WHERE clause. The following statement shows the usage of the ON clause: SELECT t.cTranID, t.dIssueDt, b.cBookID, b.cBookName,t.dActualReturnDt FROM Book b JOIN Transaction t ON (b.cBookID = t.cBookID); © SQL Star International Ltd. 175
  • 179. In the code you specify the join condition using the ON clause. The Book and the Transaction tables are joined based on the column cBookID present in both the tables. Using ON Clause with Different Column Names The ON clause can also be used to join tables using columns with different names. It is similar to a self-join, wherein you join a table with itself. The following statement shows the usage of the ON clause to create a join using columns with different names: SELECT S.nLibStaffNo StaffNo, S.cLibStaffName StaffName, S.nLibMgrNo MgrNo, M.cLibStaffName MgrName FROM LibStaff S JOIN LibStaff M ON S.nLibMgrNo = M.nLibStaffNo; In the statement, the join condition is specified in the ON clause using different columns. The query displays the following result: Creating Three-Way Joins Using ON Clause In the SQL: 1999 syntax, you can also create three-way joins. That is, you can join three tables. The join is performed from left to right. The first join is created on the first two tables. It cannot reference the third table. The second join is created on the first two tables collectively (created by the first join) and the third table. This way, all three tables are referenced in the second join. To retrieve data from the Book, Transaction and Member tables simultaneously, use three-way join clause in the following manner: SELECT m.cMemberID, m.cLastName, b.cBookName, b.cAuthorName, t.cTranID, t.dIssueDt, t.dReturnDt FROM Book b JOIN Transaction t ON (b.cBookID = t.cBookID) JOIN Member m ON m.cMemberID = t.cMemberID; In the query, the first join is created between the Book and the Transaction tables using the column cBookID. The second join is created between the Book and the Transaction tables taken together and the Member table using the column cMemberID. Once the joins are created data can be retrieved simultaneously from three tables. OUTER Joins When you use joins on two tables, it returns all rows that match the condition. In SQL: 1999 syntax, this type of join is called an inner join. © SQL Star International Ltd. 176
  • 180. When a join not only returns the result of an inner join (the matched rows), but also the unmatched rows, it is called an outer join. The unmatched rows are the ones that are deficient in information and thus, do not match the condition specified in the join condition. The information deficiency could be in the right side or the left side of the join condition. Accordingly, the join is called right outer join or left outer join. If the deficiency is on both sides of the join condition it is called full outer join. Left Outer Join Left outer join enables you to retrieve all rows (matched or unmatched) from the table specified on the left side of join condition. To retrieve information about the books that are issued as well as the books that are not issued to any members, you can give a left outer join query as follows: SELECT T.cMemberID, B.cBookName FROM Book B LEFT OUTER JOIN Transaction T ON (B.cBookID = T.cBookID); The query retrieves the names of the books that are issued to the members. However, as there is a left outer join on the Book table, the query also retrieves all books that are not issued to anybody. Book IDs of such books are however not found in the Transaction Table. From the output, you can identify member IDs to whom books have been issued. The books that are available but have never been issued have no match in the Transaction table and hence no member ID is retrieved along with it. You could get the same result on issuing the Oracle proprietary syntax as follows: SELECT T.cMemberID, B.cBookName FROM Book B, Transaction T WHERE B.cBookID= T.cBookID(+); Right Outer Join Right outer join enables you to retrieve all rows (matched or unmatched) from the table specified on the right side of join condition. The following statement specifies right outer join: SELECT M.cMemberID, M.cLastName, T.cTranID, T.cBookID, T.dissueDt, T.dreturnDt FROM Transaction T RIGHT OUTER JOIN Member M ON (T.cMemberID = M.cMemberID); The query retrieves the member details and transaction details based on the column cMemberID. The query specifies right outer join, as there may be a deficiency in the Member table (on the right side). All members may or may not issue a book from the library; hence there may not be transaction details for each member. Full Outer Join In an outer join, there can be a deficiency on both the sides of the join condition. For instance, some books may not belong to any category. This is the case when you buy a new set of books for the library and may not put them in any category for some time. You just make entries into the Book table, thereby assigning a book ID. On the other hand, a particular category may not have any books. Such situation can be handled using full outer joins, wherein both columns specified on either side of the join condition have some deficiency. © SQL Star International Ltd. 177
  • 181. To retrieve information about all books from the Book table (whether or not a book belongs to a category) and information about all categories (whether or not it contains any book), you can use a full outer join in the following manner: SELECT B.cBookID, B.cBookName, C.cCategoryName FROM Book B FULL OUTER JOIN Category C ON (B.cCategoryID = C.cCategoryID); You can also give additional conditions with full outer joins SELECT B.cBookID, B.cBookName, C.cCategoryName FROM Book B FULL OUTER JOIN Category C ON (B.cCategoryID = C.cCategoryID) AND B.cBookID = ‗CLS010009970‘; Mapping Joins The Oracle proprietary joins can be mapped to SQL:1999 syntax joins as follows: SET OPERATORS You queried multiple tables by joining them using a single query statement. You could also query multiple tables by joining two individual query statements on the different tables. This is done using any of these operators: o UNION/UNION ALL o INTERSECTION o MINUS For instance, to place a requisition for books from your supplier, you need the book list from two tables. You could: Order for all the books in both the tables – a union Order for only those books, which are there in both the tables – an intersection Order for only those books, which are there only in one of the tables - minus Assume that the New Jersey Central Library maintains two tables, BookArchive and BookProspect. The former containing details of books that have been stored in the library for quite sometime and the latter storing information of prospective books (books they intend to buy). The lists of books in the two tables as seen with a simple select statement is given below. SELECT * FROM BookArchive; CBOOKNAME © SQL Star International Ltd. 178
  • 182. ----------- Triumph Of Katie Byrne Kidnapped The Comedy of Errors The Magic Faraway Tree Oliver Twist Woman Of Substance The Humor of Humor Hamlet Wings Of The Storm Othello 10 rows selected. The list of books in the BookProspect table is: CBOOKNAME ----------- Othello David Copperfield For the New Intellectual Hamlet Sense and Sensibility The Prodigal Daughter Oliver Twist Honour Among Thieves Kidnapped The Fountainhead 10 rows selected. Union operator This operator returns the data which are unique to all the tables used in the Query. The following statement is written, when the library wants to display the list of archived and prospective books for which he has to place an order. SELECT cBookName FROM BookArchive UNION SELECT cBookName FROM BookProspect; The result it displays is: CBOOKNAME --------- David Copperfield For the New Intellectual Hamlet Honour Among Thievesl Kidnapped Oliver Twist Othello Sense and Sensibility © SQL Star International Ltd. 179
  • 183. The Comedy of Errors The Fountainhead The Humor of Humor The Magic Faraway Tree The Prodigal Daughter Triumph Of Katie Byrne Wings Of The Storm WomanOf Substance 16 rows selected. Using Union operator, all the books contained in the query tables are displayed eliminating the duplicate once. However, if you need to display the duplicates data also, you can use the union all operator. Intersect operator This operators returns the data which are common to all the tables used in the Query. By using intersect, only those books, which are common to the joined tables, are displayed. To place an order for those books that are archived and in the prospective book list issue: SELECT cBookName FROM BookArchive INTERSECT SELECT cBookName FROM BookProspect; The result of the statement is: CBOOKNAME ------------ Hamlet Kidnapped Oliver Twist Othello Minus operator This operators causes the common values to be subtracted from one of the tables and display the remaining values. For instance, to place orders for those books that are contained only in the BookProspect table and not in BookArchive, the following statement is issued: SELECT cBookName FROM BookProspect MINUS SELECT cBookName FROM BookArchive; The result of the statement is: CBOOKNAME --------- David Copperfield For the New Intellectual Honour Among Thievesl © SQL Star International Ltd. 180
  • 184. Sense and Sensibility The Fountainhead The Prodigal Daughter 6 rows selected. Guidelines for using the Set Operators 1. The number and the datatypes of the columns should always match with its corresponding query. 2. The column name in resultant would be based on the outer most SELECT statement. Summary In this session, you have learnt that:  Data present in the different tables can be extracted using the JOIN functionality in SQL. Cartesian product result when there are no joining clauses in the Statement.  Data can be obtained from multiple tables using Oracle proprietary syntax as well as using SQL: 1999 syntax.  The various Joining options in Oracle proprietary syntax are: Equijoin (based on equal value and datatype), Non-Equijoin (based on a range of valid values between the tables), Outer join (to fetch the matched as well as unmatched values) and Self join (to extract information from the same table used in lookup operation)  In SQL:1999 syntax, along with the above joins, we can also have NATURAL Join(based on same column names between the tables), FULL OUTER join (deficiency in both the tables) and CARTESIAN join(cross product) respectively.  Set operators such as UNION (extracts distinct data), UNION ALL (extracts all data from both tables), MINUS (uncommon data) and INTERSECT (common data) allow us to show data from query based on multiple tables by joining two individual query statements. © SQL Star International Ltd. 181
  • 185. Lab Exercise [Note: Questions 1 to 5 are based on Joins using the Oracle syntax. Questions 6 to 10 are based on the SQL 99 Join syntax] 1. Write a query to retrieve the first name and last name of employees along with their respective department numbers and department names as shown below. -------------------- 106 rows selected. 2. Write a query to retrieve the last name, department name, city, and commission earned of all those employees who earn a commission as shown below. 3. Write a query to retrieve the first name, last name, salary and job titles of employees belonging to department numbers 100 and 30 as shown below. © SQL Star International Ltd. 182
  • 186. 12 rows selected. 4. Write a query to retrieve the employee‘s last names, department numbers, and department names, including those departments that do not have employees. The result should be as follows: ------------ 122 rows selected. 5. Write a query to retrieve the names of each employee and their managers. The result should be as shown below. © SQL Star International Ltd. 183
  • 187. -------------------- 106 rows selected. 6. Write a query to retrieve the last names and department names of employees who have superiors. The result should be as shown below. ----------------- 7. Write a query to retrieve the names of employees and their managers. The result should be as shown below. © SQL Star International Ltd. 184
  • 188. --------------------- 106 rows selected. 8. Write a query to retrieve the last name, and department name of all employees even if the employees have not been assigned to any department. The result should be as shown below. ----------------- 107 rows selected. 9. Write a query to retrieve the employee IDs, department numbers, and department names even if employees have not been appointed to some of the existing departments. The result should be as shown below. © SQL Star International Ltd. 185
  • 189. ----------------- 122 rows selected. 10. Write a query to retrieve the employee ID, department number, and department names of those employees who have not been assigned to any department, and those departments to which employees have not yet been assigned. The result should be as shown below. © SQL Star International Ltd. 186
  • 190. Chapter 9 Understanding Subqueries    Introduction to Subqueries Types of Subqueries Guidelines for using Subqueries Single Row Subqueries using group functions Identifying illegal statements with Subqueries Multiple Row Subqueries Multiple Row Comparison Operator Impact of Null Value on the Outer Query © SQL Star International Ltd. 187
  • 191. Objectives At the end of this chapter, you will be able to: Identify the need for subqueries Write subqueries © SQL Star International Ltd. 188
  • 192. Introduction to Subqueries A subquery is a SELECT statement embedded within another SELECT statement. To understand this, look at a scenario where in you need to find the details of those who became members after ‗Celena Stevenson‘. To get the desired result, you would have to frame two queries, one query to find out the membership date of ‗Celena Stevenson‘ and the other to find out those who became members after ‗Celena Stevenson‘. By combining these two queries, i.e by placing one query inside the other you would be able to arrive at the desired result. The inner query is known as the subquery where as the outer query is called the main query. The value returned by the subquery is used as the search value in the main query. Subqueries are SELECT statements that are part of a clause of another SELECT statement. Subqueries can be embedded in any of the following SQL clauses:  FROM clause  WHERE clause  HAVING clause  ORDER BY clause The syntax to write a subquery is: SELECT select_list FROM table WHERE <column_name> operator (SELECT select_list FROM table[WHERE condition]); In the syntax, operator stands for any comparison operator such as >, =, <>, IN etc. Uses of a Subquery A subquery has the following uses: Values can be provided for the conditions specified in the WHERE, HAVING, and the START WITH clauses used in the SELECT statements. © SQL Star International Ltd. 189
  • 193. A set of rows can be defined and directly inserted into the target table of an INSERT or CREATE TABLE statement. A set of rows can be defined and included in a CREATE VIEW or SNAPSHOT statement used for creating views and snapshots . One or more values can be assigned to existing rows in the UPDATE statement. A table can be defined in a subquery and operations can be performed on it by the outer query defined by the INSERT, UPDATE and DELETE statements. Types of Subqueries The types of subqueries are: Single-row subqueries :The inner SELECT statement returns only one row. Multiple-row subqueries:The inner SELECT statement returns more than one row.  Multiple-column subqueries:The inner SELECT statement returns more than one column. Using Subqueries Before using the different types of subqueries, you must remember the guidelines to be followed while using them. © SQL Star International Ltd. 190
  • 194.  Subqueries should be enclosed within parentheses. Subqueries should be placed on the right side of the comparison operator. Subqueries cannot contain an ORDER BY clause except in a Top-n analysis. A main SELECT statement can contain only one ORDER BY clause and it must be the last clause. There are two types of comparison operators, the single row operators to be used with single row subqueries and the multiple row operators to be used with multiple row subqueries. Single-row Subqueries In single row subqueries the inner SELECT statement returns only one row. Following single row comparison operators are used in single row subqueries: • = • > • > = • < • < = • < > ‗Tifiny Keener‘, a member of the New Jersey Central Library makes a request to furnish her with details of all those members who reside in the same area as hers. But she does not mention the area where she resides. Therefore, to meet this requirement the desk officer issues the following SELECT statement: SELECT cFirstName||cLastName Name,cPhone FROM Member WHERE cArea = (SELECT cArea FROM Member WHERE cFirstName = ‗Tifiny‘ AND cLastName = ‗Keener‘); The query displays the following result: Since the library desk officer does not know the area where ‗Tifiny‘ resides, he issues an inner query to retrieve ‗Tifiny‘s‘ area and then uses the result to execute the outer query. © SQL Star International Ltd. 191
  • 195. The above example had only one condition in the WHERE clause. You can have multiple conditions too in the WHERE clause. For example, if you want to know all books written by the author who wrote the book, which has the ID ‗PSH030000017‘, and which was published after the year the book having the ID ‗NFI040000224‘ was published, issue the following statement: SELECT DISTINCT(cBookName),cAuthorName FROM Book WHERE cAuthorName = (SELECT cAuthorName FROM Book WHERE cBookID = ‗PSH030000017‘) AND dPublishedYr > (SELECT dPublishedYr FROM Book WHERE cBookID = ‗NFI040000224‘); The query displays the following result: Here the query statement contains three queries: the outer query and two inner queries. First, the two inner queries are executed returning the respective results: ‗Paul Harris‘ and ‗20-JAN-89‘. Then the outer query is executed using the values returned by the inner query to satisfy its search condition. So the query is to retrieve all those books written by ‗Paul Harris‘ and which are published after ‗20-JAN-89‘. Accessing Data from Different Tables Both the outer query and the inner query can return data from different tables. For example, based on a query made by a member of the ‗Hamilton‘ branch to display a list of all those books that belong to the ‗Fiction‘ category, the desk officer issues the following statement: SELECT cBookName,cAuthorName FROM Book WHERE cCategoryID = (SELECT cCategoryID FROM Category WHERE cCategoryName = ‗Fiction‘) AND cBranchID = ‘03HAMNJ‘; The query displays the following result: © SQL Star International Ltd. 192
  • 196. In this example, the inner query returns the ID of ‗Fiction‘ category from the Category table. The outer query then is processed using this value to extract the book details of ‗Hamilton‘ branch from the Book table. Using Group Functions in Subqueries You can also use group functions in a subquery. For example, the library management requests the desk officer to display the details of the junior most members of the library (according to their age). In order to do so, the desk officer issues the following statement: SELECT cMemberID,cFirstName,cLastName, cPhone,nAge,dMembershipDt,cGrade FROM Member WHERE nAge = (SELECT MIN (nAge) FROM Member); The query displays the following result: In this example, the inner query uses the MIN function to retrieve the lowest age of members of the library. The age retrieved is then used as a result for the outer query. You can embed subqueries not only in the WHERE clause, but also in the HAVING clause. For example, suppose that the library management is interested in knowing about those books, which are more in stock in the library, than the books written by ‗Charles Dickens‘. To fulfill this requirement the desk officer issues the following statement: SELECT cAuthorName, COUNT (cBookName) FROM Book GROUP BY cAuthorName HAVING COUNT (cBookName)> (SELECT COUNT (cBookName) FROM Book WHERE cAuthorName = ‗Charles Dickens‘); © SQL Star International Ltd. 193
  • 197. The query displays the following result: 6 rows selected. Multiple-row Subqueries Examine the query below: SELECT cMemberID, nFine FROM Transaction WHERE nFine = (SELECT MAX (nFine) FROM Transaction GROUP BY dIssueDt); The query displays an error in the following line: WHERE nFine = (SELECT MAX (nFine) * ERROR at line 3: ORA-01427: single-row subquery returns more than one row This query attempts to retrieve the IDs of those members who have paid a fine amount that is equivalent to the maximum amount of fine received on books borrowed on issue dates taken as a group. However, on executing this statement the Oracle Server displays an error message saying, ―single-row subquery returns more than one row‖. This error is encountered because in the example, the inner query contains the GROUP BY clause, which causes more than one row to be returned, that is, one result for each group. The result of the subquery is used in the WHERE clause of the outer query. But the WHERE clause uses an equal (=) operator, which is a single-row comparison operator. A single-row operator does not expect more than one value and hence generates the error. © SQL Star International Ltd. 194
  • 198. Therefore, subqueries that return more than one row is called multiple-row subqueries. You will have to change single-row comparison operator to multiple-row comparison operator in order to overcome this error. Following are the multiple-row operators: You can modify the example using the multiple-row comparison operator IN as follows: SELECT cMemberID,dIssueDt, nFine FROM Transaction WHERE nFine IN (SELECT MAX (nFine) FROM Transaction GROUP BY dIssueDt); The query displays the following result set: ------------------- 20 rows selected. ANY Operator © SQL Star International Ltd. 195
  • 199. The ANY operator is used to compare values to each value that a subquery returns and is used along with =, !=, > and < operators. On the request of the library management to retrieve the Ids of those members who have not borrowed books on ‗14-APR-01‘ and have paid a fine amount that is more than any of the amounts received by way of fines on books issued on ‗14-APR-01‘, the desk officer issues the following statement: SELECT cMemberID,cBookID, dIssueDt,nFine FROM Transaction WHERE nFine > ANY (SELECT nFine FROM Transaction WHERE dIssueDt = ‘14-APR-01') AND dIssueDt <> ‘14-APR-01'; The query displays the following rows: ------------------- 11 rows selected. This statement compares the fine amount with the fines received on books issued on ‗14-APR-01‘. Since you have used > ANY, the minimum fine amount received on ‗14-APR-01‘ is $3. SELECT nFine FROM Transaction WHERE dIssueDt = ‘14-APR-01'; The statement returns: The outer query then returns those transaction details (other than the transactions of ‗14-APR-01‘) where the fine amount is greater than $3. © SQL Star International Ltd. 196
  • 200. ALL Operator The ALL operator is used to compare a value to every value that a subquery returns. It is used along with the operators like > and <. The desk officer issues the following statement to meet the request made by the management to retrieve those transaction details wherein members have paid fine amounts exceeding the average amount of fine received on all the dates the books were borrowed from the library: SELECT cMemberID,cBookID,nFine FROM Transaction WHERE nFine > ALL (SELECT AVG (nFine) FROM Transaction GROUP BY dIssueDt); no rows selected This statement compares the fine amount with the average fines received on issue dates taken as a group. Executing the subquery below, we get the average of fines. SELECT dIssueDt,AVG(nFine) FROM Transaction GROUP BY dIssueDt; The query displays the following result set: ---------------- 20 rows selected. Since you have used >ALL, the highest average fine of an issue date is $13.5. The outer query, however, returns no rows, as there are no members whose fine amount is greater than $13.5. Errors in Subquery Statements © SQL Star International Ltd. 197
  • 201. When you write subqueries and execute them, you need to be very careful about a few issues. There may not be any technical or syntactical error but the logic is executed in such a way that will not get the required result. Impact of Null Value on the Outer Query To understand the impact of null values on outer query, look at the statement written below that displays information about a book, which is not published in the same year as books written by ‗Enid Blyton‘. SELECT cBookName,cAuthorName,dPublishedYr FROM Book WHERE dPublishedYr NOT IN (SELECT dPublishedYr FROM Book WHERE cAuthorName = ‗Enid Blyton‘); This query does not return any rows. In the above example, you are trying to display those books, not published in the same year books written by ‗Enid Blyton‘ were published. But, you get a statement saying no rows selected. This is because one of the values returned by the inner query is null as the year of publish of one of ‗Enid Blyton‘s‘ book (The Magic Faraway Tree) is unknown. You already know that when conditions compare a value to a null value, they result in null. Therefore, if null values are returned by the inner query, do not use the NOT IN operator as it is equivalent to ―not all”. But, if null values are returned by the inner query, you can use the IN operator, as it is equivalent to ―equal to any‖. SELECT DISTINCT(cBookName), cAuthorName, dPublishedYr FROM Book WHERE dPublishedYr IN (SELECT dPublishedYr FROM Book WHERE cAuthorName = ‗Enid Blyton‘); The query displays the following result set: © SQL Star International Ltd. 198
  • 202. By using the IN operator you are trying to display those books, that were published in the same year as books written by ‗Enid Blyton‘ were published. Summary In this chapter, you have learnt that:   Subqueries are used to extract unknown information from a known value. These are created by enclosing one SELECT Statement within the other.  The inner SELECT statement is known as a Subquery and outer SELECT statement is known as a Main Query.  Both the outer query and the inner query can return data from different tables.  Resultant of Outer query is based on the values fetched by the Subquery.  A subquery can return one or more number of values. Based on the return values, comparison operators are divided into single row comparison operators (relational operators) and multiple row comparison operators (ALL, ANY and IN).  Null value generated in a subquery nullifies the entire query resulting in no row selected. It can be handled restricting the NULL values using IS NOT NULL clause. © SQL Star International Ltd. 199
  • 203. Lab Exercise 1. Write a subquery to display the last name and salary of employees in the samdepartment as Nancy. 6 rows selected. 2. Write a query to retrieve the employee numbers, last names and salaries of all employees whose salary is greater than the average salary. ------------------ 49 rows selected. 3. Display the last name, department number and salary of all employees whose location ID is 1400. © SQL Star International Ltd. 200
  • 204. 4. Write a query to display the last name, department number, and salaries of all employees who report to Hunold: 5. Write a query to display last name, job ID and manager ID of employees belonging to the marketing department. ------------------ 34 rows selected. 6. Write a query to display the last names, department ID, and salaries of all employees whose department ID and salary match the department ID and salary of all employees who earn a commission. 6 rows selected. © SQL Star International Ltd. 201
  • 205. Chapter 10 Advanced Subqueries Multiple column Subqueries Pairwise and Non-Pairwise Comparison Subquery in the FROM Clause Working with Scalar Subqueries Using Correlated subqueries EXISTS and NON EXISTS operators WITH clause © SQL Star International Ltd. 202
  • 206. Objectives At the end of this chapter, you will be able to:  Use Multiple column Subqueries  Write Subqueries in FROM clause  Use Correlated subqueries  Work with EXISTS and NON EXISTS operators Use WITH clause © SQL Star International Ltd. 203
  • 207. Multiple Column Subqueries While using single-row subqueries and multiple-row subqueries, you have only compared one column in the WHERE clause or the HAVING clause. But what should be done if the need arises to compare more than one column? This can be achieved by using multiple-column subqueries, that is, subqueries that return values for more than one column. The syntax for writing this subquery is: SELECT column, column, … FROM table WHERE (column, column,…) IN (SELECT column, column, … FROM table WHERE condition); In a multiple column subquery, the WHERE clause compares columns in two ways: Pairwise and Non-pairwise. To understand these two column comparison types, let us look at some examples. Pairwise Column Comparison Generate a report with the details of a book whose category ID and number of books in that category is the same as those of books written by ‗Shakespeare‘. For example if ‗Shakespeare‘ has written four tragedies, the result should display other authors who have written four tragedies. The result should not contain details of ‗Shakespeare‘s‘ books. SELECT cBranchID,cBookName, cAuthorName,cCategoryID, nNoOfCopies FROM Book WHERE (cCategoryID,nNoOfCopies) IN (SELECT cCategoryID, nNoOfCopies FROM Book WHERE cAuthorName=‘Shakespeare‘) AND cAuthorName<>‘Shakespeare‘; © SQL Star International Ltd. 204
  • 208. The query displays the following result: ----------------- 11 rows selected. To understand how the pairwise column comparison works, look at the resultant values obtained by executing the inner query. SELECT cCategoryID, nNoOfCopies FROM Book WHERE cAuthorName= ‗Shakespeare‘; The inner query displays the following result: ------------------------ 10 rows selected. © SQL Star International Ltd. 205
  • 209. In pairwise column comparison, each row returned by the outer query must have both the category Ids and the number of copies same as that for the books written by ‗Shakespeare‘. Non-pairwise Column Comparison Generate a report with details of books whose: Category ID is same as any of Shakespeare‘s book category IDs. The number of books matches the number of books written by ‗Shakespeare‘ in any category. For example if Shakespeare has written four tragedies and two romances, the result should also contain details of books of authors who have written either two or four tragedies or romances. SELECT cBranchID,cBookName, cAuthorName,cCategoryID,nNoOfCopies FROM Book WHERE cCategoryID IN (SELECT cCategoryID FROM Book WHERE cAuthorName= ‗Shakespeare‘) AND nNoOfCopies IN (SELECT nNoOfCopies © SQL Star International Ltd. 206
  • 210. FROM Book WHERE cAuthorName= ‗Shakespeare‘) AND cAuthorName <> ‗Shakespeare‘; The query displays the following result: ------------------ 16 rows selected. © SQL Star International Ltd. 207
  • 211. Subquery in the FROM Clause So far you have written subqueries in the WHERE clause and the HAVING clause. You can also embed a subquery in the FROM clause. The query uses a FROM clause subquery: SELECT T.cMemberID, T.cBookID, T.nFine, TR.FineAvg, T.dIssueDt FROM Transaction T, (SELECT dIssueDt, AVG(nFine) FineAvg FROM Transaction GROUP BY dIssueDt) TR WHERE T.dIssueDt = TR.dIssueDt AND T.nFine > TR.FineAvg; The query displays the following result: © SQL Star International Ltd. 208
  • 212. 6 rows selected. This example displays the member IDs, the book IDs, fine amount, average fines and the issue dates of those members who have paid a fine amount, which is more than the average fines paid for that issue date. In the above statement, the Transaction table is given the alias T and the FROM clause subquery (which returns value from the Transaction table) is given the alias TR. This is similar to self-join. The WHERE clause compares the issue dates of the Transaction table with the issue dates returned by the subquery and also the fine amount is compared with the average fines for all issue dates that are returned by the subquery. Scalar Subqueries A scalar subquery is a subquery that returns exactly one column value from one row. It is used to specify a scalar value returned from an expression. You cannot qualify multiple column subqueries as scalar subqueries. The value of a scalar subquery expression is the number of rows returned by the SELECT statement in the scalar subquery. The data type of the return value should match the value being selected in the subquery. If the number of rows returned by the scalar subquery expression is zero, the value of the scalar subquery is NULL. If the number of rows returned by the scalar subquery is more than one, the Oracle server returns an error. This is because, a scalar subquery must return exactly one column value from one row. In Oracle8i, scalar subqueries were supported in the following cases: SELECT statement (FROM, WHERE clauses) VALUES list of an INSERT statement The enhancements made in Oracle9i enable you to use scalar subqueries in all valid expressions like: © SQL Star International Ltd. 209
  • 213. All clauses of a SELECT statement, except the GROUP BY clause Conditions and expressions used in CASE and DECODE functions The SET clause, on the left hand side of the operator The WHERE clause of the UPDATE statement Scalar subqueries cannot be used in certain cases, such as:  Default values for columns  The basis for function-based index  A returning clause in DML statements  In HAVING clauses  In GROUP BY clause, CHECK constraints and WHEN condition  In Hash expressions for clusters  In START WITH and CONNECT BY clauses  In statements such as CREATE PROFILE that are not related to queries A Scalar Subquery in CASE Expression The following example demonstrates the use of a scalar subquery in CASE expression. To retrieve the ID and name of all books belonging to the category ‗Fiction‘ in the branch ‗Randolph NJ Library‘, you can use CASE expression in scalar subquery. SELECT cBookID, cBookName, (CASE WHEN cCategoryID = (SELECT cCategoryID FROM Category WHERE cCategoryName = ‗Fiction‘) THEN ‗Fiction‘ ELSE ‗Others‘ END) Category FROM Book WHERE cBranchID = ‘04RANNJ‘; It has an outer query that retrieves the IDs and the names of the books stored in branch ‗04RANNJ‘ from the Book table. The CASE expression evaluates the category of the book depending on the result of the inner query. The inner query returns the category ID of books belonging to the category ‗fiction‘. When you execute this scalar query, the inner query is executed first. The Oracle server looks into each row of the Category table and compares the value of © SQL Star International Ltd. 210
  • 214. cCategoryName column. If it is ‗Fiction‘, then it returns its category ID to the outer query. Based on the value of category ID returned, the Oracle server assigns the value ‗Fiction‘ to category, else assigns ‗Others‘. The output is: ------------------ 38 rows selected. A Scalar Subquery in ORDER BY Clause A scalar subquery can be used in ORDER BY clause. To retrieve the ID and names of books stored in branch ‗01ADLNJ‘ in the order of category, you must issue the following query: SELECT cBookID, cBookName FROM Book b WHERE cBranchID = ‘01ADLNJ‘ ORDER BY (SELECT cCategoryName FROM Category c WHERE b.cCategoryID = c. cCategoryID); The query is sorted based on the category name, which is retrieved by the scalar subquery that matches the category ID in the Book table with the category ID in the Category table. The query retrieves the following output: © SQL Star International Ltd. 211
  • 215. -------------------------------- 31 rows selected. A Scalar Subquery in Functions A scalar subquery can be used as an argument to built-in functions, user-defined functions and type constructors. For instance, you want to retrieve the book name and the first three letters of category. You can give a scalar subquery in the SUBSTR function and retrieve the first three letters of the category. This is shown in the following code: SELECT cBookName,SUBSTR((SELECT cCategoryName FROM Category c WHERE c.cCategoryID = b.cCategoryID) ,1,3)Category FROM Book b; In the code, the inner query is executed first. Matching the category ID from the Category table and the category ID from the Book table retrieves the category of the book. As this query is in the SUBSTR function, the letters from position one to three are only retrieved. Then, the outer query is executed, which retrieves the book name from the Book table. The output is shown in the following screenshot: ----------------- 184 rows selected. © SQL Star International Ltd. 212
  • 216. Correlated Subqueries Correlated subqueries are also a type of nested subqueries, but execute differently. In nested subqueries, the inner query executes first and the resulting value is used by the outer query. However, in correlated subqueries, the execution is the opposite. The outer query is executed first and the result is used by the inner query. In other words, the inner query is driven by outer query. Correlated subqueries are used whenever every row in a table must be processed and evaluated to generate a result. The Oracle server performs a correlated subquery whenever a subquery references a column from a table specified in the outer query (or the parent statement). A correlated subquery involves row-by-row processing of the table specified in the parent statement. These rows are also known as candidate rows. It reads every candidate row and compares the values in each row against a related data. Following steps take place when a correlated subquery is executed: 1. The candidate row is retrieved (from the outer query or the parent statement) 2. The value of the candidate row is used by the inner query 3. The result of the inner query is used to qualify or disqualify the candidate row 4. The above steps are repeated for all candidate rows The syntax of a correlated subquery is: SELECT column1, column2 FROM table1 parent WHERE column1 operator (SELECT column1, column2 FROM table2 WHERE expresion1 = parent.expression2); You can use a correlated subquery to find out all members whose age is greater than or equal to the average upper age of their grade. Following is the code: SELECT cFirstName, nAge, cGrade © SQL Star International Ltd. 213
  • 217. FROM Member m WHERE nAge >= (SELECT AVG(nUpperAge) FROM MemberFee WHERE cGrade = m.cGrade); This query uses a correlated subquery where the cGrade column of the table from outer query is used in the inner query. The inner query calculates the average upper Age of all members belonging to each grade fetched by the outer query. The inner query result is used by the outer query. The outer query looks into all records of the Member table and displays only the records where the age of a member is greater than or equal to the average upper age of members belonging to a grade. The result of the query is as follows: EXISTS Operator in Correlated Subqueries All types of logical operators can be used with nested subqueries. In addition to these, you can use the EXISTS operator, which is mostly used with correlated subqueries. The EXISTS operator tests whether a row value exists in the resultset of inner query. If the row value is found in the inner query, the condition is flagged as TRUE, and the search is discontinued. This holds good for the first occurrence of the row value in the inner query. If the row value is not found in the inner query, the condition is flagged as FALSE and the search is continued in the inner query. If you want to find out the Library staff members who have at least one person reporting to them, you can use the following correlated subquery with an EXISTS operator: SELECT nLibStaffNo, cLibStaffName FROM LibStaff l WHERE EXISTS (SELECT ‗x‘ FROM LibStaff WHERE nLibMgrNo=l.nLibStaffNo); On executing the query, the following result is obtained: © SQL Star International Ltd. 214
  • 218. In the query, the nLibStaffNo and the cLibStaffName columns of the LibStaff table are retrieved from the outer query. In the inner query, the search begins from the first row of the nLibMgrNo column of the LibSatff table. The value in the nLibMgrNo is matched with the value in the nLibStaffNo column of the LibStaff table (of the outer query). If a match is found, the condition becomes TRUE and the result of the outer query is displayed. The EXISTS operator ensures that the search does not continue further. Note that in the inner subquery, a constant ‗x‘ is used in the SELECT statement. This is done for performance reasons. As the EXISTS operator does not return any specific value but only checks for the existence of a value in a column, it is advisable to give a constant in the SELECT statement. This is because, having a column name in the SELECT statement causes a table scan for that column, which affects the performance. Alternatively, you can use the IN construct to get the same result as the EXISTS operator. SELECT nLibStaffNo, cLibStaffName FROM LibStaff l WHERE nLibStaffNo IN (SELECT nLibMgrNo FROM LibStaff WHERE nLibMgrNo IS NOT NULL); The NOT EXISTS Operator The NOT EXISTS operator works in a manner opposite to the EXISTS operator. It checks whether a row value selected in the outer query does not exist in the inner query and flags a TRUE condition. If it exists, it flags FALSE. You can use the NOT EXISTS operator to find the categories for which the library has not stored any books. SELECT cCategoryID, cCategoryName From Category c Where NOT EXISTS (SELECT ‗x‘ © SQL Star International Ltd. 215
  • 219. FROM Book WHERE CCategoryID=c.cCategoryID); The query is a correlated subquery. The outer query selects the category ID and the category name from the Category table. The inner query selects constant value from the Category table and compares the category ID with the category ID selected from the outer query. If the two categories match, a FALSE condition is flagged (as NOT EXISTS operator is used). If the category ID in the inner query does not match with the category ID in the outer query, the condition becomes TRUE and the columns from the outer query are returned. Thus, the above code retrieves all categories that do not have an entry in the Book table, meaning those categories that do not have any books. The result of the query is as follows: Alternatively, you can use NOT IN operator in place of NOT EXISTS operator to get the same result. This is shown in the following example: SELECT CategoryID, cCategoryName From Category c Where cCategoryID NOT IN (SELECT cCategoryID FROM Book); However, if the result of the inner query contains even a single NULL value, the NOT EXISTS operator evaluates to FALSE. Therefore, the query will not return any rows even if the WHERE condition is satisfied. WITH Clause In a complex query, it is possible that a query block is used more than once or has many references. Executing the same query block repeatedly is not advisable from performance standpoint. The WITH clause also known as subquery_factoring_clause can be used in such cases. It:  Enables you to use the same query block in a SELECT statement  when it is referenced more than once in a complex query  Retrieves the results of the query block and stores it in the user‘s  temporary table space, thereby improving performance © SQL Star International Ltd. 216
  • 220. Allows you to define a query block before using it in a query  Can hold multiple query blocks separated by commas  Improves performance, as the calculations in the invoked subquery  are done only once  Is resolved as in-line view or a temporary table Using a WITH clause you can improve the readability and maintainability of SQL statements. It allows you to separate the business logic from data gathering. Internally the WITH clause is resolved as an in-line view or a temporary table. You can use a WITH clause to find out the issue dates on which the total fine collected is greater than the average fine collected. Following is the code: WITH TotFinePerIssDt AS ( SELECT dIssueDt, SUM(nfine) fine_tot FROM Transaction GROUP BY dIssueDt), AvgFinePerIssDt AS ( SELECT SUM(fine_tot)/count(*) fine_avg FROM TotFinePerIssDt) SELECT * FROM TotFinePerIssDt WHERE fine_tot> (SELECT fine_avg FROM AvgFinePerIssDt) ORDER BY dIssueDt; In the code the WITH clause creates two query blocks TotFinePerIssDt and AvgFinePerIssDt. The TotFinePerIssDt query block retrieves the total fine collected on every issue date. The AvgFinePerIssDt query block calculates the average of the total fine collected on each issue date. To calculate this, AvgFinePerIssDt query block takes the total fine values from TotFinePerIssDt query block. Finally, the query retrieves the total fine that is greater than the average of the total fine collected on each issue date. Without a WITH clause the query would be very complex, and the use of several SELECT statements would affect the performance. By using a WITH clause, you can write a code which is easy to read and maintain. In addition, the results of each query block is stored in a temporary tablespace and used every time it is referenced, thereby enhancing the performance. © SQL Star International Ltd. 217
  • 221. There are some points you should remember while using a WITH clause. A WITH clause can:  Be used with SELECT statements only  Hold more than one query, each of which is separated by a comma.  Create a query block, which is available to all WITH element query blocks defined after it and the main query block.  Have a query block with the same name as an existing table name, where the query block name is given priority Summary In this chapter you have learnt that:  Multiple columns in a WHERE clause can be used by writing multiple column subqueries. © SQL Star International Ltd. 218
  • 222. Comparison in multiple column subqueries are done using Pairwise (exact values are searched) and Non-Pairwise (combination of values are searched for) comparisons.  Subqueries written in a FROM clause helps us to create a virtual column (non existent column) for calculation purpose. This query is also known as Inline View.  Scalar subqueries can be written in a CASE expression, in a Function and in an ORDER BY clause. © SQL Star International Ltd. 219
  • 223. Lab Exercise 1. Write a query to display the last names, department ID and salaries of all employees whose department ID and salary match the department ID and salary of all employees who earn a commission. ----------------- 34 rows selected. 2. Display the last name, department name and salary of all employees whose salary and department name are same as the salary and department name of employees located in location ID 1700. ---------------- 18 rows selected. 3. Write a query to display details of employees who have one or more colleagues in their department who joined after them, with higher salaries. © SQL Star International Ltd. 220
  • 224. ------------------ 66 rows selected. 4. Display the details of employees who are not managers. [Hint: Use the NOT EXISTS operator. Also, use the NOT IN operator and see the result]. ---------------- 89 rows selected. © SQL Star International Ltd. 221
  • 225. Chapter 11 Data Manipulation Various types of INSERT statements Create UPDATE statements Generate DELETE statements Single set Aggregate in DML RETURNING Clause Transaction command to Save and discard changes Locking Mechanism Show how Read consistency works © SQL Star International Ltd. 222
  • 226. Objectives At the end of this chapter, you will be able to:  Describe the Data Manipulation Language  Perform 10g Single Set Aggregates in DML  Control the Database Transaction © SQL Star International Ltd. 223
  • 227. Manipulating Data In the previous sessions, the library database users have only extracted the data stored in the database. For instance, when a member wishes to see a list of all the books stored in the library, the desk officer issued a simple SELECT statement as follows: SELECT * FROM Book; However, when the desk officer issues the same statement after a few days, he may observe some noticeable variations in the resultant output. For instance, there would be additions to the already existing list of books, or a particular book may no longer be stocked. This reflects that the data stored in the database is dynamic in nature. These changes involve:  Adding new data  Modifying existing data  Removing data This chapter deals with how a database developer should implement these changes. These changes are made possible by the use of Data Manipulation Language (DML). The following DML statements are executed in order to manipulate the data in the database:  INSERT  UPDATE  DELETE  MERGE Insert Rows In every organization, the new data or additional data must necessarily be incorporated into the database. For example, when people enroll themselves as members of the New Jersey Central Library, their details must be added to the Member table. Similarly, details regarding new books ordered by the library should be inserted into the Book table. In order to add new data to the tables, use the INSERT statement. Its syntax is: INSERT INTO table [(column [, column…])] VALUES(value [, value…]); © SQL Star International Ltd. 224
  • 228. N.B.: [This is not a complete syntax.] Where, table is the name of the table into which new column values are inserted. (column [, column…]) are the columns of the specified table into which the values are inserted. (value [, value…]) these are the actual values that are inserted into the columns specified. There are different ways of inserting data into a table using the above syntax. Ways of Inserting Data The Oracle server enables you to insert data into the database in the following four ways:  Inserting values for each column  Inserting values for selected columns  Inserting values using substitution variables  Inserting values from another table Inserting a Row Containing Values for Each Column Suppose the library has ordered for a ‗Paul Scott‘ book. When the book is delivered, the librarian has to enter the relevant information into the Book table. To do so, the following INSERT statement should be issued: INSERT INTO Book (cBookID,cBookName,cAuthorName, cCategoryID,cPublisherID, dPublishedYr,cBranchID, nNoOfCopies) VALUES (‗FIC011111111‘,‘Jewel In The Crown‘, ‗Paul Scott‘,‘01FIC‘,‘HC0176',‘25-NOV-1966', ‘01ADLNJ‘, 2); 1 row created. The INSERT statement tends to become quite cumbersome, especially when all the details of a book must be added. To resolve this issue, Oracle makes it optional to specify the column list in the INSERT clause, if a row being inserted contains values for each column. © SQL Star International Ltd. 225
  • 229. INSERT INTO Book VALUES (‗FIC011111111‘,‘Jewel In The Crown‘, ‗Paul Scott‘,‘01FIC‘,‘HC0176',‘25-NOV-1966',‘01ADLNJ‘, 2); 1 row created. But, in the above statement how would you know what data will be inserted into which column? This is achieved by listing values in the VALUES clause according to the position of columns in the table. In order to determine the default order of the columns in the table, use the iSQL*Plus DESCRIBE command. For example to view the structure of the table Book, use the following code: DESCRIBE Book While using the INSERT statement, you need to remember the following points: Enclose character and date values in the VALUES clause within single quotation marks.  You can also insert pseudo columns such as SYSDATE, USER (displaying the current users name) and conversion functions. Inserting Rows that Contain Values Only for Some Columns In the above example, on the arrival of the new book, the entire details are inserted into the Book table using the INSERT statement. However, at times the library may not have all the details of a new book. For instance, on the delivery of a new book ‗Roots‘, the library did not have details of its publisher. In such a case, only the available details are inserted and the remaining columns are left null, so that they can be inserted later. To insert null values, the Oracle server provides two methods:  Implicit Method  Explicit Method Implicit Method © SQL Star International Ltd. 226
  • 230. In this method, you can omit those columns from the column list, into which values are not to be inserted. The following INSERT statement specifies only those columns into which values are to be inserted: INSERT INTO Book (cBookID, cBookName, CAuthorName, cCategoryID, cBranchID) VALUES (‗FIC051111112‘,‘Roots‘,‘ALEX HUXELY‘,‘01FIC‘,‘05PRINJ‘); Ensure that these columns allow null values. You can verify this using the iSQL*PLUS DESCRIBE command. Explicit Method In this method, specify the NULL keyword in the values list for those columns into which values are not to be inserted. The above INSERT statement could be rewritten as follows: INSERT INTO Book VALUES (‗FIC051111112‘,‘Roots‘,‘ALEX HUXELY‘,‘01FIC‘,NULL,NULL,‘05PRINJ‘,NULL); This statement omits the column list in the INSERT clause. In the VALUES clause, the NULL keyword is specified in place of all those columns whose values are not known. Inserting Rows Using Substitution Variables Till now you have inserted only single rows into a table. However, in reality you would be required to insert multiple rows. For instance, a library would always place a bulk order for books. In such a scenario, you can imagine how tedious it would be to issue that many INSERT statements. This can be made easier if the user is prompted to enter the new values each time. This is achieved by using the iSQL*PLUS substitution variables. You can insert details of a bulk order of books delivered using substitution variables as follows: INSERT INTO Book (cBookID, cBookName, cAuthorName, cCategoryID, cPublisherID, dPublishedYr, cBranchID, nNoOfCopies) VALUES (‗&BkID‘, ‗&BkName‘, ‗&Author‘, ‗&CatgID‘,‘&PubID‘, ‗&PubYr‘, ‗&BrnID‘, &Copies); © SQL Star International Ltd. 227
  • 231. Inserting Rows from Another Table The New Jersey Central Library maintains an IncompleteTransaction table to store details of those transactions where members have not returned the borrowed books for more than six months. Instead of inserting these details manually, Oracle provides an option of populating the table with values derived from an existing table, which in this case is the Transaction table. This is achieved by using a subquery instead of the VALUES clause in the INSERT statement. Its syntax is as follows: INSERT INTO table [column (, column)] subquery; Remember that the number of columns and their datatypes specified in the column list must be the same as the number of columns and their datatypes specified in the subquery. The following example illustrates how the usage of the subquery in the INSERT statement populate the IncompleteTransaction table. INSERT INTO IncompleteTransaction SELECT cTranID, cMemberID, cBookID, dIssueDt, dReturnDt, dActualReturnDt, nFine FROM Transaction WHERE dActualReturnDt IS NULL AND (SYSDATE-dIssueDt) > 185; 2 rows created. You can view the values inserted into the IncompleteTransaction table. SELECT * FROM IncompleteTransaction; Displays: CTRANID CMEMBERID CBOOKID DISSUEDT DRETURNDT DACTUALRE NFINE ------- --------- ------ ------- -------- --------- ----- T0000300100 CBW109702 ROM020003211 07-SEP-00 21-SEP-00 © SQL Star International Ltd. 228
  • 232. T0000241000 CRB038901 PSH010000010 11-OCT-00 25-OCT-00 Update Data Just as you enter details of new members in the Member table, similarly any change in the members‘ information, such as their address, requires you to incorporate these changes effectively in the database tables. Such changes in the existing data are made using the UPDATE statement. The syntax for using the UPDATE statement is: UPDATE table SET column = value [, column = value,…] [WHERE condition]; Where, table is the name of the table you are attempting to update. column is the column in the specified table whose value is to be updated. value is the new value with which the old column value is to be replaced. condition specifies the condition for the rows to be updated Variations in Updating Data Oracle provides different ways in which you can update the data in a database table. These are:  Updating Specific or all the Rows  Updating Using Subqueries  Updating Rows Using Values from Other Tables Updating Specific or all the Rows In order to update specific row(s), you must specify the WHERE clause in the UPDATE statement. For example, a library member Jessica Hatcher has intimated the change in her address and phone number. In order to incorporate these changes the following UPDATE statement is to be issued: UPDATE Member SET vAddress = ‗112, Rockturn Manor Apts.Second Cross Rd‘, cPhone = ‗9678111903‘ © SQL Star International Ltd. 229
  • 233. WHERE cFirstName = ‗Jessica‘ AND cLastName = ‗Hatcher‘; 1 row updated. In this example if the WHERE clause had been omitted, all the members‘ address and phone numbers would have been updated. However, it is advisable to use the primary key column in order to update a specific row. This is due to the using of non-primary key columns (such as cFirstName and cLastName) that may cause other rows to be updated too. For instance in the above example, you used the member name to identify the specific row that is to be updated. It works fine as long as there is only one member with the name Jessica Hatcher. But it could cause a problem if the library has more than one member with the same name. Updating Using Subqueries In order to update column values for specific rows with already existing values of the table you can use subqueries in the SET clause of the UPDATE statement. For example, suppose the ‗Dorrance‘ publishing company shifts its company location to the same area as that of the Blackwell publishing company, then you need to update ‗Dorrance‘ publishing company‘s address to that of Blackwell publishing company‘s address. This can be achieved using subquery in the UPDATE statement. We will First have a look at its syntax: UPDATE table SET (column, column,…) = (SELECT column, column,… FROM table WHERE condition) WHERE condition; The syntax is same as an UPDATE statement, except that the SET clause contains columns whose values are updated using values retrieved from subqueries. Now use this syntax to update the above-mentioned change in the PublisherDetails table. UPDATE PublisherDetails SET vPublisherAddress= (SELECT vPublisherAddress © SQL Star International Ltd. 230
  • 234. FROM PublisherDetails WHERE cPublisherName= ‗Blackwell‘) WHERE cPublisherName=‘Dorrance‘; 1 row updated. Updating Rows Using Values from Other Tables Just as you can populate a table using values from an existing table, similarly you can update rows by using subqueries that return values from other tables. For example, suppose the New Jersey Central Library creates a table, RandolphBks having a structure similar to the Book table and populated with details of books stored only in the ‗Randolph NJ Library‘. The library management may decide to update the number of copies of books stored in the above created table with the number of copies of book number ‗MYS010000001‘ from the Book table as follows: UPDATE RandolphBks SET nNoOfCopies = (SELECT nNoOfCopies FROM Book WHERE cBookID=‘MYS010000001'); 38 rows updated. Using Explicit Default Values In Oracle9i, enhancements were introduced with regard to the usage of the DEFAULT keyword. Whenever the DEFAULT keyword is used, the default value specific to the column is applied. This is a feature of the SQL: 1999 standard. The benefit of using this feature is that, data integrity is ensured, and you need not hard code literals in your applications. You can specify a default value for the columns. Later, whenever you use the DEFAULT keyword, the default value is taken for that column. If you do not specify a default value for a column, then the Oracle server sets the column to null. Explicit DEFAULT can be used in INSERT and UPDATE statements. For instance, when the New Jersey Central Library procures a new set of books, entry for the new books is made in the Book table. Initially you may not decide upon © SQL Star International Ltd. 231
  • 235. the categories to which the books belong. Therefore, you put them in a common category. Under such circumstances, you can set the default value for the category ID in the Book table and make entries. Here, the default value is set as ‗01HUM‘. First, alter the Book table to modify the category column to take the default value as ‗01HUM‘. ALTER TABLE BOOK MODIFY cCategoryID DEFAULT ‘01HUM‘; Now, you can make new entries in the Book table as follows: INSERT INTO Book(cBookID, cBookName, cCategoryID, cPublisherID, cBranchID) VALUES (‗XYZ0135599555‘,‘Fish‘, default, ‗PN0135‘, ‗01ADLNJ‘); When you execute this query, book details are entered into the Book table. However, for the category of the book, the default value is entered. You can also use the DEFAULT keyword in UPDATE statements to set default values for the columns. In the following query we will change the category ID of the book ‗Fun With Maths and Physics‘ to the default value of category ID, that is, ‗01HUM‘. UPDATE Book SET cCategoryID=DEFAULT WHERE cBookName=‘Fun With Maths and Physics‘; Delete Data © SQL Star International Ltd. 232
  • 236. The purpose of creating a database and maintaining it is to ensure that it truly reflects the changes taking place in the real world. For instance, if library member Nina Philip terminates her membership with the library, retaining her details in the Member table does not serve any purpose. You can remove any such unnecessary data using the DELETE statement. Its syntax is: DELETE [FROM] table [WHERE condition]; The DELETE statement removes the entire rows unlike the INSERT and UPDATE statements, which allow the adding of values to specific columns or updating only specific column values. In order to delete specific column values, set their values to null using the UPDATE statement. Since the WHERE clause is optional, omitting it will cause all the rows to be deleted. Ways of Deleting Rows There are two ways of deleting data from tables. These include removing:  All or specified data  Data using subqueries Removing Specific Rows or All Rows By specifying the WHERE clause you can delete specific row or rows. For instance, the New Jersey Central Library maintains a NonMember table, wherein the details of ex-members are stored. Their details are used to communicate any new schemes the library comes up with. However, the details of those non-members are deleted who fail to respond to any correspondence sent to them. DELETE FROM NonMember WHERE cFirstName = ‗Susan‘ AND cLastName = ‗Philip‘; 1 row deleted. © SQL Star International Ltd. 233
  • 237. Deleting Rows Using Subqueries Similar to inserting and updating rows using subqueries, you can delete rows from a table by using values returned by the subquery, written in the WHERE clause. For example, due to lack of response to any of the correspondence made by the library to non-members of the Hamilton NJ Library branch, the management decides to delete their details from the NonMember table as follows: DELETE FROM NonMember WHERE cBranchID = (SELECT cBranchID FROM Branch WHERE cBranchName = ‗Hamilton NJ Library‘) 2 rows deleted. In this example, the subquery returns the branch ID of Hamilton branch. This value is then used in the WHERE clause of the DELETE statement. © SQL Star International Ltd. 234
  • 238. Single set aggregates in DML RETURNING clause Oracle10g Offers new enhancements that allow the use of single-set aggregate functions in the returning clause of the DML statements. This can result in significant performance gains in transactions that process many rows of the same table - such as in batch processes. The DML statements that can use the single-set aggregates in their returning clauses are INSERT, UPDATE and DELETE. We will begin with the INSERT statement. Single-set Aggregates in the INSERT Statement The general format for the INSERT statement when using a RETURNING clause for a single table insert, using the INTO clause is shown below. INSERT INTO <table or expression> <alias> (column,?) <values_clause>|<subquery> RETURNING <exprs> INTO <data_items>; Where, table or expression is a valid table, materialized view, single-table view, or an expression based on one of the above. alias is a valid alias for the table or expression. Column is a comma-separated list of column names or a single column name. Values clause is a valid values clause to be used to provide inserted values. Subquery is a valid subquery to generate inserted values exprs is a set of expressions based on the affected row data_items is a valid set of variables into which values are returned by the expressions Single-set Aggregates in the UPDATE Statement When the target of the UPDATE is a single row, the RETURNING clause can retrieve column expressions using the affected row, rowid, and REFs to the affected row. Single-set aggregates can only be used when the returning clause returns a single row. These aggregates cannot be combined with simple expressions in the same returning clause. © SQL Star International Ltd. 235
  • 239. An example of UPDATE using the RETURNING clause and a single-set aggregate is shown below. SQL> VARIABLE Total_Fine NUMBER SQL> UPDATE Transaction SET nfine=nfine*0.5 RETURNING SUM(nfine) INTO :Total_Fine; SQL> PRINT Total_Fine Single-set Aggregates in the DELETE Statement The general format for the DELETE statement when using a RETURING clause for a single table delete is shown below. DELETE <table or expression> <alias> WHERE <where_clause> RETURNING <exprs> INTO <data_items>; Transactions Transaction, in simple words is a series of data manipulation statements executed as one logical unit of work. But, why are DML statements executed as one logical unit of work? This could be understood by looking at the outcome of treating data manipulating statements as individual activities. An act of a customer purchasing a product of certain quantity, is a transaction, which comprises of two different activities:   Updating the stock level of the product in Product table  Entering the cash received details in the CashTransaction table. But, after making the payment if the customer decides to change the quantity of the product purchased, then Oracle would not be able to undo the stock level updates or © SQL Star International Ltd. 236
  • 240. the cash received at entry, as these two activities have been saved to the Oracle database individually. Hence, the changes will not be reflected in the respective tables. This is because we have treated them as two individual activities independent of each other. But in reality when a product is purchased both the activities involved are performed simultaneously. Therefore, a collection of DML statements is executed as a single unit of work, which is a transaction. The act of purchasing a product affects more than one table. However, if you wanted to reverse the transaction would it get reflected in all the required tables? Controlling your transactions can solve this problem. The different types of transactions are:  DML transactions that comprise any number of DML statements treated as one unit of work  DDL (Data definition language) transactions that comprise only one DDL statement  DCL (Data control language) transactions that comprise only one DCL statement Controlling Transactions You can control transactions using transaction control mechanisms. Transaction control mechanism comprises of a set of commands that define the beginning, end and breakpoint of a transaction. These commands are called transaction control commands and are as follows:  COMMIT permanently saves the data changes  ROLLBACK discards all data changes  SAVEPOINT divides a transaction into different sections Using Transaction Control Commands There are two ways to control transactions, which are:  Explicit transaction control  Implicit transaction control Explicit transaction control © SQL Star International Ltd. 237
  • 241. To control the transactions explicitly you need to use the COMMIT, ROLLBACK and SAVEPOINT control statements. Each of these is explained below . COMMIT The COMMIT statement is issued when the user is satisfied with all the changes made and therefore is ready to save them to the database. Issuing a COMMIT statement ends the current transaction and begins a new one. For example, the following DML statement is issued on the Member table to update the phone number of Stanley Davenport: UPDATE Member SET cPhone=‘9865457989' WHERE cFirstName=‘Stanley‘ AND cLastName=‘Davenport‘; 1 row updated. But before issuing a COMMIT statement the state of data in the Member table would be as follows:  Other users cannot change all those rows that are currently being changed by another user. This is known as the locking of rows.  Changes made to the data get reflected only in the SQL buffer and not in the database. Therefore the previous state of the data can be recovered if you want to discard the changes made.  The current user can view the result of the DML statements, by using the SELECT statement. But other users cannot view the changes, as the changes have not yet been permanently saved to the database. SELECT cPhone FROM Member WHERE cFirstName=‘Stanley‘ AND cLastName=‘Davenport‘; CPHONE ---------- 9865457989 But after issuing a COMMIT statement as follows: © SQL Star International Ltd. 238
  • 242. COMMIT; Commit complete.  Changes to the data are made permanent in the database, hence, the previous state of the data cannot be recovered.  All users can view the result of the DML operations as the changes are permanently saved to the database.  Other users can now perform new data changes as the locks on the rows are released. ROLLBACK The ROLLBACK statement is issued when the user wants to discard changes made to the data before they are committed and made permanent. If the user deletes rows that should not be deleted, the deletion could be undone by issuing the ROLLBACK statement. For example, you may accidentally delete all the rows from the Transaction table while attempting to delete only one record from the table. DELETE FROM Transaction; 32 rows deleted. Issuing the ROLLBACK keyword and then writing the correct transaction can undo this. ROLLBACK; Rollback complete. DELETE FROM Transaction WHERE dIssueDt=‘05-MAY-2001'; 2 rows deleted. COMMIT; Commit complete. ROLLBACK statement not only undoes the current transaction, but also marks the beginning of a new one. State of the data before ROLLBACK is similar to that before COMMIT. But after ROLLBACK,  © SQL Star International Ltd. 239
  • 243.  All changes to data are undone.  Previous state of the data is recovered. In the example you can check the status by issuing a SELECT statement for the Transaction table library database.  Other users can perform new changes to data as the locks on the rows are released. During the execution of a transaction, if a DML statement fails, only its effect is rolled back. But all the other data changes made by the previous DML operations are not scraped away. This kind of functionality is performed implicitly. For example, while attempting to delete Shakespeare‘s book details from the Book table, the following error message is displayed and the effect of the DML operation is rolled back implicitly: DELETE FROM BOOK WHERE cAuthorName=‘Shakespeare‘; DELETE FROM BOOK * ERROR at line 1: ORA-02292: integrity constraint (SCOTT.TRANSACTIONBOOKIDFK) violated – child record found You receive the child record found violation error because you have attempted to delete ‗Shakespeare‘ books from the Book table, which are being referenced in the Transaction table. Such errors are known as Integrity Constraint Errors and are covered in depth in the subsequent chapters. SAVEPOINT Issuing a ROLLBACK statement ends the current transaction by discarding all the changes made to the data. But, a user may not always want to discard all the changes made, simply because the last statement issued contains changes which are unwanted. Therefore, divide the transaction into different segments so that you can discard those segments you want to while keeping the rest intact. The syntax to use SAVEPOINT is: SAVEPOINT name; For instance assume that you have executed the following transaction in the library database: INSERT INTO Transaction VALUES (‗T000300501‘,‘BJH029405', ‗MYS010000065‘,‘11-MAY-2001',‘25-MAY-2001' © SQL Star International Ltd. 240
  • 244. ,NULL,NULL); 1 row created. SAVEPOINT InsertTran; Savepoint created. UPDATE Transaction SET dActualReturnDt= ‘27-MAY-2001' WHERE cTranID=‘T000300501'; 1 row updated. SAVEPOINT UpdateTran; Savepoint created. DELETE FROM Transaction WHERE cTranID=‘T000300501'; 1 row deleted. In the example, the transaction has been divided into small sections by using the SAVEPOINT statement. In case you want to rollback any of these transactions, then you will have to issue the ROLLBACK TO SAVEPOINT clause, which rolls back the current transaction to the specified savepoint. So, all the changes made after the savepoint are discarded. If this clause were omitted, the ROLLBACK statement would discard the entire transaction. Hence, to rollback the transactions to a particular point only, add the following statement: ROLLBACK TO UpdateTran; Rollback complete. In the example, the ROLLBACK TO UpdateTran clause rolls back the deletion made after the issue of the savepoint UpdateTran, while keeping the insertion and updation, made prior to the savepoint, intact. When Does a Transaction begin and end? A transaction begins when the Oracle server encounters the first executable SQL statement written by the user on logging on to the SQL*PLUS environment. The SQL statement could be DML, DDL or DCL statement. A transaction ends on the occurrence of the following: © SQL Star International Ltd. 241
  • 245.  Saving or committing  Execution of a DDL or DCL statement because they automatically save the activities performed  A user exiting from the SQL*PLUS environment.  Machine failure When one transaction ends, the next transaction begins with the next executable SQL statement. Implicit Transaction Control Implicit transaction controls do not involve the use of transaction control commands. Instead, the functionality of these commands automatically occurs under different circumstances. Automatic Commit Under the following circumstances, an automatic commit occurs:  Issue of a DDL or a DCL statement, or  Normal exit from SQL*PLUS environment, or  Keeping the SQL*PLUS, AUTOCOMMIT command on. Therefore, as soon as each DML statement is executed, it is committed. Hence, they cannot be rolled back. Automatic Rollback An automatic rollback occurs when the user exits from SQL*PLUS environment abruptly, i.e. shutting down the machine without following the normal exit routine or if the system crashes. In either case the entire transaction is rolled back and the initial state of the data, as it was at the time of the last commit, is returned. This prevents unwanted changes to be made to the data. © SQL Star International Ltd. 242
  • 246. Locking Mechanism Different users access the database to perform different operations. Database users accessing the database perform the following two types of operations:  Read operations to retrieve data from the database but not make any modifications to it (SELECT statement)  Write operations to perform modifications to the data in the database (INSERT, UPDATE, DELETE statements) Therefore it is necessary to ensure that the users reading from and writing to the database get a consistent view of the data at all times. This is referred to as read write consistency. Read consistency is needed to ensure that,  Both, the database reader as well as the writer gets a consistent view of the data.  Readers get to see the data that is not in the process of being changed.  A change made by one writer does not conflict with changes made by another writer. The tool used to achieve this is locking. In order to prevent data from being modified by more than one user, the Oracle server uses the locking mechanism, which requires no user effort. It is fully automatic and occurs for all SQL statements except SELECT. Locks are broadly classified into two types namely: 1. DML Locks Or Data Locks  Table level Locks  Row level Locks 2. DDL Locks What Happens when Row-Level Lock is placed on Row? First a DML Lock is placed on the row.  No Other Transaction Can Lock Or Update this Row  This Lock will be released when the locking transaction commits or rollback. Secondly, a DDL Lock is placed on the table, containing the row, to prevent anyone from altering or dropping the table while the row is undergoing the update. What happens when a Table level Lock is placed on the table? © SQL Star International Ltd. 243
  • 247.  Only the table Locking Transaction can Update Rows in the table  No rows in the table can be updated by other transactions  The whole table is Locked  Other Transaction can query the table, including the one being updated in the table - Writers won‘t block Readers.  Transactions that query the table will be redirected to the rollback data to satisfy the query. The following example illustrates the locking mechanism. ‗Lisa Carmen‘ attempts to update the number of copies of the book ‗Fractals Everywhere‘ in the Book table. The Oracle server keeps a copy of the data before it is updated into a segment within the server known as the rollback segment. Before she commits the change she will be able to view the modifications made to the data. But all other users will see only the copy kept in the rollback segment. Therefore, when user ‗Matt Scummen‘ attempts to read data from the Book table, he will get the data that is kept in the rollback segment. This ensures that the database readers get data that is not currently being modified. After ‗Lisa Carmen‘ commits the DML operation, the change is made permanent to the database. It now becomes visible to anyone attempting to execute a SELECT statement. So, now when ‗Matt Scummen‘ issues a SELECT statement he gets the new updated data. The space that was occupied by the old data in the rollback segment is released so that it can be reused. Instead, if ‗Lisa Carmen‘ decides to rollback the DML operation, the Oracle server writes the data kept in the rollback segment back to the table. Therefore, all the users are able to see the data as it existed before the transaction began. Read Consistency Consider 2 users using the same table for two different operations as shown in the table below. © SQL Star International Ltd. 244
  • 248. When user2 queries the Member table after some time he gets the old telephone no (9865457989) till the time user1 commits. Summary In this chapter, you have learnt that:  Data within the database can be manipulated using the Data Manipulation command (DML).  The various DML commands are, © SQL Star International Ltd. 245
  • 249. INSERT: Adding new values into table, UPDATE: modifying the existing values DELETE: removing the values and MERGE: adding and modifying data based on the condition in a single statement.  These DML commands can be made interactive using the substitution variables (‗&‘) in the scripts.  RETURNING INTO clause can be used in DML statement to view modifications done by the DML operation. This feature avoids using another SELECT statement to see the changed value.  Transaction can either be saved or undone using Data Transaction Control Statement. COMMIT statements make the transaction permanent and ROLLBACK statement reverses all the un-committed transaction.  Rows in a table undergoing a change, gets implicitly locked. Explicit locks can also be applied on the tables.  Only committed data is viewed by all the users. This is known as read consistency. © SQL Star International Ltd. 246
  • 250. Lab Exercise [Note: For questions 1 to 8, you are required to insert, update and delete data from the OfficeStaff table.] To work with the OfficeStaff table, run the LabEx11_00.sql script file. This creates the OfficeStaff table. The structure of the table is as follows: The rows to be inserted are given below. 1. From the sample data given above, insert the first row into the OfficeStaff table without listing the columns in the INSERT clause. © SQL Star International Ltd. 247
  • 251. 2. Insert the second row from the sample data into the OfficeStaff table by explicitly listing the columns in the INSERT clause. Confirm the creation of rows. 3. Create a script file LabEx11_03.sql. Within the file write an INSERT statement to populate the OfficeStaff table. The INSERT statement should be such that it prompts you to enter the required values. To produce values for the Mail_ID column, concatenate the first letter of first name with the last names. 4. Now run the script file to insert the next two rows of sample data. Make the data inserted permanent. Confirm the rows inserted into the OfficeStaff table. 5. Increase ‗Susan Bright‘s‘ salary by 10%. 6. Remove the details of ‗Morgan Sheen‘ from the OfficeStaff table. Confirm the changes made. Commit the changes made. 7. Insert the last row of the sample data. Mark a savepoint immediately after inserting the row. 8. Delete all the rows from the OfficeStaff table. Confirm that the table is empty. Now,rollback the DELETE statement, but ensure that the earlier INSERT statement is not discarded. Make the transaction permanent. 9. Write a query to update the salary of the employees working in department number 10 by 10% and using the returning clause to print the updated value. © SQL Star International Ltd. 248
  • 252. Chapter 12 Managing Tables Data Definition Language Datatypes used in Defining columns Modifying Table Structure Manipulating Table Definition Flashback Table © SQL Star International Ltd. 249
  • 253. Objectives At the end of this chapter, you will be able to:  Create tables  Identify the datatypes used when defining the columns  Modify table structure  Understand Flashback table © SQL Star International Ltd. 250
  • 254. Introduction In order to store data in an organized manner, Oracle provides data containers known as Database Objects. Oracle also provides a mechanism by which you can create and manipulate them. To understand the creation of database objects, you must first know the different types of database objects. Database Objects Any data structure created within the database for a specific purpose is known as a database object. Oracle provides various database objects, which are as follows: Table for storing data View for providing a customized view of data from one or more tables Sequence for generating numeric column values that serve as primary keys Index to retrieve data faster from the database Synonym to give alternative names to other database objects In order to create the above listed database objects, you must use a language that supports database object creation. The language provided by SQL for database object creation, modification and removal is the Data Definition Language or DDL. Data Definition Language Data Definition Language (DDL) comprises of a set of SQL commands that are used to: Create database objects Alter database objects Drop database objects Truncate rows with the database objects  Rename the database objects The DDL commands that perform the above-mentioned tasks are: CREATE ALTER TRUNCATE DROP  RENAME © SQL Star International Ltd. 251
  • 255. Creating Tables A table is a database object that stores data. Here, the data is stored in the form of rows and columns. Each row consists of one or more columns. The DDL statement used to create a table in the database is CREATE TABLE. CREATE TABLE Statement To create a table with the CREATE TABLE statement, the syntax is as follows: CREATE [GLOBAL TEMPORARY] TABLE [schema.] <table_name> (Column datatype [DEFAULT expr] [,….] ); Where, GLOBAL TEMPORARY specifies that the data in the table is temporary where as the table definition is permanent. In other words, the data is visible only in the session in which it was inserted, but the table definition is visible in all sessions. schema is same as the user name table_name is the name of the table DEFAULT expr specifies a default value that a column should have column is name of the column datatype specifies the datatype and the length of a column Given below is an example that creates a table named Branch, with columns to store ID, name, address, location, phone and the year during which the branches were established. CREATE TABLE Branch (cBranchID NUMBER(7), cBranchName CHAR(25), vBranchAdress VARCHAR2(50), cBranchLocation CHAR(15), cPhone CHAR(10), dEstbl DATE ); When the table is created, the following message is displayed. Table created. © SQL Star International Ltd. 252
  • 256. To view the columns and their datatypes in the Branch table, issue the command DESCRIBE in the following manner: DESCRIBE Branch Schema When a database is created, several users access it. A single user does not create all the database objects. Database objects are created by each user as and when required. Database tables are usually created just once as they make up the basic database. When many users create objects, there is a security issue. To prevent the users from tampering with each other‘s objects, every user is allotted a separate work area. A user is allowed to create database objects in his work area and use them. There is no physical demarcation of memory area for different users. It is a logical allotment of memory area. Database objects created by one user are logically separate from the database objects created by other users. Such logical collection of database objects such as tables, views or sequences is known as a schema. For example, the tables named Member and Book are created by the DBA. Hence, the DBA becomes the owner of the tables and the tables become a part of the DBA schema. To reference the objects created by a user, prefix the object name with the schema or owner name. For instance, to refer to the Member table you would refer to it as DBA.Member Table Naming Conventions To improve readability and avoid common mistakes, some naming conventions need to be followed. They include: Keeping short and descriptive names. For example, it would be hard to comprehend a table named as Bk_iss_trans. Instead, you could name it Transaction. © SQL Star International Ltd. 253
  • 257.  Giving same name to the columns having same values in different tables. For example, category ID are present in Book as well as the Category table. So give them the same name, cCategoryID. Rules to be followed when naming tables are: All tables must begin with an alphabet. All column names must be in lowercase. Names can be up to 30 characters long. You cannot use non-alphanumeric characters except the underscore (_), the dollar sign ($) and the hash mark (#). The names must not be the same as that of any other object owned by the user. The names must not be an Oracle server keyword such as SELECT, CREATE, INSERT etc. Setting Default Values Specifying default values for columns at the time of creating tables saves the task of entering values for them during an insert. If a row is inserted without a value for a column then this option prevents null values from being entered into that column. Literal values, expressions or SQL functions can be used as the default value. For example, in the Member table, a default value for the dMembershipDt column can be defined, so that when new member details are to be inserted, their membership date is set by default to SYSDATE. dMembershipDt DATE DEFAULT SYSDATE Create Tables Using Subqueries When a table is created, initially it does not contain any value. A table is populated using the INSERT statement. However, you can create tables with pre-populated data. That is, you can create a table with the same structure and data as another table. You can create a table with pre-populated data by using a subquery in the CREATE TABLE statement. © SQL Star International Ltd. 254
  • 258. The syntax to perform this task is: CREATE TABLE <table_name> [(column, column…)] AS subquery; Where, table_name is the name of the table. column is the name of the column. You need not specify the columns that the table must have if the subquery SELECT statement retrieves all the columns. There are certain guidelines that need to be followed.  While defining columns, mention only the column names and if necessary the default values. Do not define their datatypes and width.  The number of columns defined must be the same as the number of columns mentioned in the SELECT clause.  If columns were not defined then the column names of the table created would be the same as the column names specified in the subquery. For example, the user DBA creates the IncompleteTransaction table for the library to store details of those books, which have been issued six months back and have not yet been returned by members. The data for this table comes from the Transaction table. Inserting rows into the former table will prove to be quite cumbersome, if there are large number of members who have not returned books in the past six months. Instead, these details could be directly populated from the Transaction table, as both the tables are similar in structure. The code to solve this problem is: CREATE TABLE IncompleteTransaction AS SELECT * FROM Transaction WHERE dIssueDt>(SYSDATE – 6) AND dActualReturnDt IS NULL; Table created. The code selects all those details from the Transaction table, where members have not returned books issued more than six months back and populates them into IncompleteTransaction table. SELECT * FROM IncompleteTransaction; © SQL Star International Ltd. 255
  • 259. Displays the following output: CTRANID CMEMBERID CBOOKID DISSUEDT DRETURNDT DACTUALRE NFINE -------- --------- ------------ --------- --------- --------- ----- T0000300100 CBW109702 ROM020003211 07-SEP-00 21-SEP-00 T0000241000 CRB038901 PSH010000010 11-OCT-00 25-OCT-00 Datatypes Used When Defining Columns To create tables, you need to decide what kind of data you want to store in the tables. Are they number or text? This brings us to the issue of datatypes. Datatypes help us identify the type of data that can be entered in a column. The datatypes that have been used so far are alphanumeric datatypes such as VARCHAR2 and CHAR, numeric datatype such as NUMBER and the DATE datatype. Character Datatype This datatype is used to store character values. CHAR datatype supports character data up to a maximum length of 2000. It pads the column value with blanks up to the length declared after taking up the required space for the value. VARCHAR2 datatype allows you to store character data up to a maximum length of 4000. VARCHAR2 does not pad up the blank cells. In addition to the above datatypes, the other character datatypes available in the Oracle database are: Number Datatype The datatype used to store only numeric data is the number datatype, NUMBER (precision, scale). It can store both fixed and floating-point numbers. By precision we mean the total number of digits and scale is the number of digits to the right of the decimal point. For example, 779.69 is number datatype where the precision is 5 and the scale is 2. In the Member table, member‘s age is stored as NUMBER datatype. © SQL Star International Ltd. 256
  • 260. Date Datatype In Oracle, dates are stored in the DATE datatype, which actually contains two values: the date, and the time between January 1, 4712 BC and December 31, 9999 AD. The default date format in which Oracle stores date is DD-MON-YY where DD is the day of the month (01), MON is the month (Jan) and RR is the year (two-digit year-99, 01). DATETIME Datatype This datetime datatype had been introduced in Oracle9i. The datetime datatype includes the time zone in the date and time data, as well as provide support for fractional seconds. New datetime functions are also provided to use these datatypes. These datatypes and functions ease the development of applications accessed globally and significantly reduce the cost of developing and deploying applications. Applications that are deployed across the globe include time zones and multi- language support through Unicode. The datetime datatypes are time zone sensitive and adjust the datetime as per the session time zone of the user. The datetime datatypes are based on the concept of time zones and Greenwich Mean Time (GMT), now known as Coordinated Universal Time (UTC). The time along the prime meridian in Greenwich, England is known as Greenwich Mean Time (GMT). The meridian line is an imaginary line that runs from the North pole to the South pole. The earth is divided into 24 time zones depending on the hours of a day. UTC is the standard time, which is same all around the year. It does not change by summer time or daylight savings time. All time zones in the world refer to the UTC. When it is noon in Greenwich, it is midnight along the international line. The datetime datatypes include: TIMESTAMP data type TIMESTAMP WITH TIME ZONE TIMESTAMP WITH LOCAL TIME INTERVAL data type INTERVAL YEAR TO MONTH INTERVAL DAY TO SECOND © SQL Star International Ltd. 257
  • 261. TIMESTAMP Datatype The TIMESTAMP data type allows time to be stored as a date with fractional seconds. It is an extension of the DATE datatype and stores the year, month and day of the DATE datatype along with the hour, minute and seconds. Apart from this, it also stores the fractional value of seconds. The TIMESTAMP datatype has the following form: TIMESTAMP[(fractional_seconds_precision)] Where, fractional_seconds_precision specifies the number of digits in the fractional part of the SECOND datetime field. It can be any number ranging from 0-9. For instance, create a table AdmissionDetails with a column of type TIMESTAMP. CREATE TABLE AdmissionDetails ( StudentName VARCHAR2(20), Address VARCHAR2(20), AdmissionDate TIMESTAMP(7), Fees NUMBER(7,2) ); In AdmissionDetails table, the AdmissionDate column is of type TIMESTAMP and of precision ‗7‘, which indicates the fractional seconds precision. If you do not specify the precision, the default is 6. Now, insert two rows into the table. When you execute the following query. SELECT admissiondate FROM Admissiondetails; The output is as follows: 25-NOV-20 01.00.00.0000000 AM 01-OCT-20 01.00.00.0000000 AM The TIMESTAMP datatype has the following variations:  TIMESTAMP WITH TIME ZONE data type TIME STAMP WITH LOCAL TIME data type © SQL Star International Ltd. 258
  • 262. TIMESTAMP WITH TIME ZONE TIMESTAMP WITH TIME ZONE datatype is an extension of TIMESTAMP and stores year, month, day, hour, minute, second with fractional seconds, TimeZone hour and TimeZone_minute or TimeZone_region. It has the following format: TIMESTAMP[(fractional_seconds_precision)] WITH TIME ZONE Two values of TIMESTAMP WITH TIME ZONE datatype are considered identical if they represent the same instant in UTC, regardless of the TIME ZONE offset. For instance, TIMESTAMP ‗2000-02-15 9:00:00 +8‘ is identical to TIMESTAMP ‗2000-02-15 3:00:00 +2‘ Here, ‗+8‘ is the time zone offset of Singapore. ‗+2‘ is the time zone offset of Egypt. As the difference in the values of the two offsets is six hours, 9:00 AM in Singapore is same as 3:00 AM in Egypt. Create a table AdmissionDetails1 with a column admission date of type TIMESTAMP WITH TIME ZONE. Insert two records and see the output. CREATE TABLE AdmissionsDetails1 (StudentName VARCHAR2(20), Address VARCHAR2(20), AdmissionDate TIMESTAMP WITH TIME ZONE, Fees NUMBER(7,2) ); Table created. Insert some values into the table AdmissionDetails1 by selecting data from AdmissionDetails table. INSERT INTO AdmissionDetails1 © SQL Star International Ltd. 259
  • 263. SELECT * from AdmissionDetails; Now, you select the admission date from the newly created table AdmissionDetails1 table: SELECT AdmissionDate from AdmissionDetails1; Following is the output, which shows the Time Zone offset from UTC, as ‗+5:30‘: ADMISSIONDATE ------------- 25-NOV-20 01.00.00.000000 AM +05:30 01-OCT-20 01.00.00.000000 AM +05:30 TIMESTAMP WITH LOCAL TIME ZONE TIMESTAMP WITH LOCAL TIME ZONE is another variation of the TIMESTAMP datatype that includes a time zone displacement in its value. Data stored in the database is converted to the database time zone. However, the time zone offset is not stored as a part of the column data. When a user selects a data, the server returns the value according to the user‘s session time zone. For example, a Singapore database has system time zone offset of ‗+8‘. If a user from India (with session time zone offset ‗+5.30‘) uses the Singapore database, TIMESTAMP WITH LOCAL TIME ZONE data is adjusted as follows:  The user in India inserts a TIMESTAMP value ‗10-NOV-2001 9:00:00 +5:30‘ into a TIMESTAMP WITH LOCAL TIME ZONE column in Singapore database. The inserted data is stored in Singapore database as ‗10-NOV-2001 11:30:00‘. Note the difference in time from ‗9:00‘ to ‗11:30‘. This is due to a difference of ‗+2:30‘ hours between the offset of Singapore and India time zone.  Later, when the client in India retrieves the same data from Singapore database, the value displayed in India is‗10-NOV-2001 9:00:00 ‘. The Oracle database returns the data in the user‘s local session time zone.   Whereas, a client in Singapore retrieves the same data, the value displayed is ‗10-NOV-2001 11:30:00‘ © SQL Star International Ltd. 260
  • 264. The format of TIMESTAMP WITH LOCAL TIME ZONE datatype is: TIMESTAMP[(fractional_seconds_precision)] WITH LOCAL TIME ZONE Create a table with TIMESTAMP WITH LOCAL TIME ZONE datatype. Insert some data into it. Try to retrieve the same data from a different session. You will see the difference in time, as the Oracle database returns the data in the user‘s local session time zone. This session is started in the time zone of India. Later you can change the time zone and see the difference in time. CREATE TABLE AdmissionsDetails2 ( StudentName VARCHAR2(20), Address VARCHAR2(20), AdmissionDate TIMESTAMP WITH LOCAL TIME ZONE, Fees NUMBER(7,2) ); The code creates a table called AdmissionDetails2 with AdmissionDate of type TIMESTAMP WITH LOCAL TIME ZONE and other columns of their respective datatypes. Insert some rows into the table as follows: INSERT INTO AdmissionDetails2 SELECT * FROM AdmissionDetails1; When you retrieve data within the column AdmissionDate from the table AdmissionDetails2, the output shows the time as per current time zone: SELECT AdmisionDate FROM AdmissionDetails2; © SQL Star International Ltd. 261
  • 265. ADMISSIONDATE ------------------- 25-NOV-20 01.00.00.000000 AM 01-OCT-20 01.00.00.000000 AM 04-MAR-01 09.30.00.000000 PM Change the time zone to Singapore time zone in the following manner: ALTER SESSION SET TIME_ZONE = ‗+8:00‘; Session altered. Now if you select the AdmissionDate column from AdmissionDetails2 table, you get the following output: SELECT AdmisionDate FROM AdmissionDetails2; ADMISSIONDATE ------------------------- 25-NOV-20 03.30.00.000000 AM 01-OCT-20 03.30.00.000000 AM 05-MAR-01 12.00.00.000000 AM As the difference between time zone of Singapore and time zone of India is two and a half hours, the time displayed in the output shows a difference of two and a half hours in each entry. Therefore, a user in Singapore will see the output according to Singapore local time zone and a user in India will see the output according to Indian local time zone. This is possible with the help of TIMESTAMP WITH LOCAL TIME ZONE datatype. The INTERVAL Datatype The INTERVAL datatype is used to store a period of time. A period of time is the difference between two datetime values. The period can be years, months, days, hours, minutes or seconds. Therefore the interval datatype comprises of two types: INTERVAL YEAR TO MONTH datatype INTERVAL DAY TO SECOND datatype The INTERVAL qualifier may specify a leading field precision, which specifies the number of digits that can be present in a leading field. © SQL Star International Ltd. 262
  • 266. INTERVAL YEAR TO MONTH datatype The INTERVAL YEAR TO MONTH datatype stores a period of time using YEAR and MONTH datetime fields. It is specified as follows: INTERVAL YEAR[(year_precision)] TO MONTH Where, year_precision is the number of digits in the YEAR datetime field. The default value of year_precision is ‗2‘. For instance, INTERVAL ‗21-5‘ YEAR(2) TO MONTH indicates an interval of 21 years and 5 months INTERVAL ‗21-5‘ YEAR(2) indicates an interval of 21 years INTERVAL ‗5‘ MONTH(2) indicates an interval of 5 months Create a table LEASE that has a lease_time column of INTERVAL YEAR TO MONTH datatype, with year_precision value as ‗2‘ and insert some values for year and month. CREATE TABLE Lease ( lease_time INTERVAL YEAR(2) TO MONTH ); Table created. INSERT INTO Lease VALUES(INTERVAL ‗10‘YEAR(2)); INSERT INTO Lease VALUES(INTERVAL ‗11‘ MONTH); INSERT INTO Lease VALUES(INTERVAL ‗3-9‘ YEAR TO MONTH); INSERT INTO Lease VALUES(‗5-10‘); SELECT Lease_time FROM Lease; The output is: LEASE_TIME ---------- +10-00 +00-11 +05-10 The first INSERT statement inserts the value for year as ‗10‘. The year takes a precision of ‗2‘ as specified during table creation. If you try to insert a value of three © SQL Star International Ltd. 263
  • 267. digits, Oracle server gives an error. The second INSERT statement inserts a value for month as ‗11‘. The third INSERT statement inserts values for both year as well as month as ‗3-9‘. INTERVAL DAY TO SECOND Datatype The INTERVAL DAY TO SECOND datatype stores a period of time in days, hours, minutes and seconds. The format is: INTERVAL DAY[(day_precision)] TO SECOND For instance, INTERVAL ‗5 03:15:20‘ DAY TO SECOND indicates an interval of 5 days, 3 hours, 15 minutes and 20 seconds. INTERVAL ‗10 00:00:00‘ DAY TO SECOND indicates an interval of 10 days, 0 hours, 0 minutes and 20 seconds. Let us create a table MATCH with a column StartDt of INTERVAL DAY TO SECOND datatype with a precision value of ‗2‘ and insert some values into it. CREATE TABLE Lease1 (StartDt INTERVAL DAY(2) TO SECOND); INSERT INTO Lease VALUES( INTERVAL ‗9 02:30:15‘ DAY TO SECOND); INSERT INTO Lease VALUES( INTERVAL ‗15 10:20:30‘ DAY TO SECOND); SELECT * FROM Lease1; The output is as follows: +09 02:30:15.000000 +15 10:20:30.000000 In the above CREATE statement, when we declare a column of DAY TO SECOND datatype with a precision value of ‗2‘, it indicates that we can insert a value of two digits per DAY. If we insert more than two digits, the Oracle server gives an error. In the first INSERT statement, we inserted a time period of 9 days, 2 hours, 30 minutes and 15 © SQL Star International Ltd. 264
  • 268. seconds. In the second INSERT statement, we inserted a time period of 15 days, 10 hours, 20 minutes and 30 seconds. Datetime Functions You have seen the various datetime datatypes. Now you will learn about the datetime functions, which enable you to retrieve the current session and database time for all datetime datatypes. The datetime functions are: CURRENT_DATE CURRENT_TIMESTAMP LOCALTIMESTAMP SYSTIMESTAMP DBTIMEZONE SESSIONTIMEZONE EXTRACT FROM_TZ TO_TIMESTAMP TO_TIMESTAMP_TZ TO_YMININTERVAL TO_DSINTERVAL TZ_OFFSET CURRENT_DATE CURRENT_DATE returns current date and time in the session time zone as DATE datatype (without fractional seconds). The value returned is in the form of Gregorian calendar date value. In earlier releases, current date and time could be retrieved using SYSDATE. However, using CURRENT_DATE, you can see the time zone changes as well. You can change the time zone of a session using the ALTER SESSION command. Retrieve the current date and time of the session by giving the following code: ALTER SESSION SET NLS_DATE_FORMAT = ‗DD-MON-YYYY HH24:MI:SS‘; ALTER SESSION SET TIME_ZONE = ‗+05:30‘; SELECT SESSIONTIMEZONE, CURRENT_DATE FROM DUAL; The output is: SESSIONTIMEZONE CURRENT_DATE --------------- ------------ +05:30 19-FEB-2002 15:10:19 Now you alter the session to time zone of Singapore. © SQL Star International Ltd. 265
  • 269. ALTER SESSION SET TIME_ZONE = ‗+8:00‘; SELECT SESSIONTIMEZONE, CURRENT_DATE FROM DUAL; The output is: SESSIONTIMEZONE CURRENT_DATE --------------- ------------------- +08:00 19-FEB-2002 17:44:45 As you can see from the output, CURRENT_DATE is relative to the session time zone. Any change in the session time zone is reflected in the time value. In the first ALTER SESSION statement, the session is altered to the time zone of India, whereas, in the second statement the session is altered to the time zone of Singapore. Therefore, when you retrieve the current date, it shows the time of respective timezones. CURRENT_TIMESTAMP The CURRENT_TIMESTAMP function returns the current date and time of the session in the form of TIMESTAMP WITH TIME ZONE datatype. The following code retrieves the SESSIONTIMEZONE and CURRENTTIMEZONE from ‗DUAL‘: ALTER SESSION SET TIME_ZONE = ‗02:00‘; SELECT SESSIONTIMEZONE, CURRENT_TIMESTAMP FROM DUAL; The output is: SESSIONTIMEZONE CURRENT_TIMESTAMP --------------- ------------------ +02:00 19-FEB-02 12.21.06.000001 PM +02:00 As shown in the output, CURRENT_TIMESTAMP returns date and time as TIMESTAMP WITH TIME ZONE type, with time zone as ‗+2‘. Now change the time zone to ‗-5‘ as shown below: ALTER SESSION SET TIME_ZONE = ‗-05:00‘; SELECT SESSIONTIMEZONE, CURRENT_TIMESTAMP FROM DUAL; © SQL Star International Ltd. 266
  • 270. The output is: SESSIONTIMEZONE CURRENT_TIMESTAMP --------------- ----------------- -05:00 19-FEB-02 05.37.07.000001 AM -05:00 The CURRENT_TIMESTAMP returns current date and time with time zone as ‗-5‘. LOCALTIMESTAMP The LOCALTIMESTAMP function returns the current date and time in the session time zone. However, the value returned is of TIMESTAMP datatype. The difference between CURRENT_TIMESTAMP and LOCALTIMESTAMP functions is that the former returns a value of type TIMESTAMP WITH TIME ZONE, whereas, the latter returns a value of type TIMESTAMP. The following code illustrates this difference: SELECT CURRENT_TIMESTAMP, LOCALTIMESTAMP FROM DUAL; The output is: CURRENT_TIMESTAMP LOCALTIMESTAMP -------------- ------------ 19-FEB-02 05.55.41.000000 AM -05:00 19-FEB-02 05.55.41.000000 AM Now alter the session: ALTER SESSION SET TIME_ZONE = ‗+02:00‘; SELECT CURRENT_TIMESTAMP, LOCALTIMESTAMP FROM DUAL; Displays: CURRENT_TIMESTAMP LOCALTIMESTAMP ----------------- ------------- 19-FEB-02 01.01.59.000000 PM +02:00 19-FEB-02 01.01.59.000000 PM Note the difference between the values returned. The CURRENT_TIMESTAMP returns the date and time along with the time zone, whereas the LOCALTIMESTAMP does not. SYSTIMESTAMP The SYSTIMESTAMP function returns date and time of the server in TIMESTAMP format, whereas the SYSDATE function (of previous releases) returns only server system date and time. © SQL Star International Ltd. 267
  • 271. SELECT SYSTIMESTAMP, SYSDATE FROM DUAL; The output is: SYSTIMESTAMP SYSDATE ------------------------ ------------------ 19-FEB-02 04.40.05.000000 PM +05:30 19-FEB-2002 16:40:05 Observe that SYSTIMESTAMP returns date and time in TIMESTAMP format. DBTIMEZONE The DBTIMEZONE function returns the default database time zone. You can set the default database time zone at the time of database creation by specifying the SET TIME_ZONE clause of the CREATE DATABASE statement. If not specified, the time zone of the operating system where the database is installed is taken as the default database time zone. SELECT DBTIMEZONE FROM DUAL; The output is: DBTIME ------- -05:00 The return value can have the following formats, depending on how the user has specified the database timezone: A character type time zone offset in the format ‗[+ | - TZH:TZM]‘ A time zone region name The output of the above select statement shows that the database time zone is ‗-5:00‘: SESSIONTIMEZONE The SESSIONTIMEZONE function returns the time zone of the current session. It can have the following format, depending on the time zone specified during database creation: A character type time zone offset in the format ‗[+ | - TZH:TZM]‘ A time zone region name © SQL Star International Ltd. 268
  • 272. Give the following statement to view the session‘s time zone: SELECT SESSIONTIMEZONE FROM DUAL; The output is: SESSIONTIMEZONE --------------- +05:30 Observe that the values for database time zone and session time zone are different . EXTRACT The EXTRACT expression extracts the value of a specified datetime field from a datetime or interval field value. Using the EXTRACT function, you can extract any of the components specified in the EXTRACT function syntax: SELECT EXTRACT([YEAR][MONTH][DAY][HOUR] [MINUTE][SECOND][TIMEZONE_HOUR] [TIMEZONE_MINUTE][TIMEZONE_REGION] [TIMEZONE_ABBR] FROM [datetime_value_expression] [interval_value_expression]); When you extract -  A TIMEZONE_REGION or TIMEZONE_ABBR (abbreviation), the return value is a string containing the appropriate time zone name or abbreviation From a datetime with a time zone, the value returned is in UTC Any other values, the value returned is in Gregorian calendar format. The following query extracts the month from the system date: SELECT EXTRACT (MONTH FROM SYSDATE) FROM DUAL; © SQL Star International Ltd. 269
  • 273. The output is: EXTRACT(MONTHFROMSYSDATE) ------------------------- 5 Give the following query to extract the year from the membership date of all the members belonging to grade ‗B‘: SELECT EXTRACT (YEAR FROM dMembershipDt) from Member WHERE cGrade = ‘B’; The output is: EXTRACT(YEARFROMDMEMBERSHIPDT) ------------------------------ 1990 1997 1999 2001 1994 1997 6 rows selected. FROM_TZ The FROM_TZ function converts a timestamp value to a TIMESTAMP WITH TIME ZONE value. The syntax of the FROM_TZ function is: FROM_TZ(timestamp_value, time_zone_value) Where time_zone_value is a character string in the format ‗TZH:TZM‘ or a character expression that returns a time zone region string TZR, like ‗ Asia/Singapore‘ or ‗America/Chicago‘. For instance, to convert to the time stamp value of the date 25th May‘2001 to a TIME STAMP WITH TIME ZONE value, give the following query: SELECT FROM_TZ(TIMESTAMP ‗2001-05-25 10:15:20‘, ‗5:00‘) FROM DUAL; The output is: FROM_TZ(TIMESTAMP‘2001-05-5 10:15:20',‘5:00') --------------------------------------------- 25-MAY-01 10.15.20.000000000 AM +05:00 © SQL Star International Ltd. 270
  • 274. Alternatively, you can also specify the TZR (time zone region) name in the query as follows: SELECT FROM_TZ(TIMESTAMP ‗2001-05-25 10:15:20‘, ‗Asia/Singapore‘) FROM DUAL; The output is: FROM_TZ(TIMESTAMP‘2001-05-2510:15:20',‘ASIA/SINGAPORE‘) ------------------------------------------------------- 25-MAY-01 10.15.20.000000000 AM ASIA/SINGAPORE TO_TIMESTAMP The TO_TIMESTAMP function is used to convert a string of CHAR, VARCHAR2, NCHAR, or NVARCHAR2 datatype to a TIMESTAMP datatype. The syntax is: TO_TIMESTAMP (char,[fmt],[‗nlsparam‘]) Where, fmt is optional. It specifies the format of char. However, if it is not specified, the string must be in the default format of TIMESTAMP datatype. nlsparam is also optional. It specifies the language in which day and month names and abbreviations are returned. It can have the form: ‗NLS_DATE_LANGUAGE = language‘ If not specified, the TO_TIMESTAMP function takes the default language selected for your session. To convert a date specified as string to a TIMESTAMP value, give the following query: SELECT TO_TIMESTAMP(‗2001-11-25 10:15:20‘,‘YYYY-MM-DD HH:MI:SS‘) FROM DUAL; © SQL Star International Ltd. 271
  • 275. The output of the above query is: TO_TIMESTAMP(‗2001-11-2510:15:20‘,‘YYYY-MM-DDHH:MI:SS‘) ------------------------------------------------------- 25-NOV-01 10.15.20.000000000 AM Observe that the TO_TIMESTAMP function converts the date specified in YYYY-MM- DD format to TIMESTAMP datatype format which is DD-MON-YY. TO_TIMESTAMP_TZ The TO_TIMESTAMP function is used to convert a string of CHAR, VARCHAR2, NCHAR or NVARCHAR2 datatype to a TIMESTAMP WITH TIME ZONE datatype. The syntax is: TO_TIMESTAMP_TZ (char,[fmt],[‗nlsparam‘]) Where, - fmt is optional. It specifies the format of char. However, if it is not specified, the string must be in the default format of TIMESTAMP WITH TIME ZONE datatype. - nlsparam is also optional. It specifies the language in which day and month names and abbreviations are returned. It can have the form: ‗NLS_DATE_LANGUAGE = language‘ If not specified, the TO_TIMESTAMP function takes the default language selected for your session. To convert a date specified as string to a TIMESTAMP WITH TIME ZONE value, give the following query: SELECT TO_TIMESTAMP_TZ(‗2002-01-12 10:15:20 +8:00‘,‘YYYY-MM-DD HH:MI:SS TZH:TZM‘) FROM DUAL; © SQL Star International Ltd. 272
  • 276. The output of the above query is: TO_TIMESTAMP_TZ(‗2002-01-1210:15:20+8:00‘,‘YYYY-MM-DHH:MI:SSTZH:TZM‘) --------------------------------------------------------------------- 12-JAN-02 10.15.20.000000000 AM +08:00 Observe that the output displays the time zone also. The TO_TIMESTAMP_TZ function converts the date specified in YYYY-MM-DD format to TIMESTAMP WITH TIMEZONE datatype format, which is DD-MON-YY. TO_YMINTERVAL The TO_YMINTERVAL function is used to convert a string of CHAR, VARCHAR2, NCHAR or NVARCHAR2 datatype to an INTERVAL YEAR TO MONTH datatype. The INTERVAL YEAR TO MONTH datatype stores a period of time using the YEAR and MONTH datetime fields. The format of the INTERVAL YEAR TO MONTH is as follows: INTERVAL YEAR [(year_precision)] TO MONTH Where, year_precision is the number of digits in the YEAR datetime field. The default is 2. The syntax of TO_YMINTERVAL function is: TO_YMINTERVAL(char) Here, char is the string to be converted. To calculate a lease period that is one year and two months after current date, give the following query: SELECT SYSDATE,SYSDATE+TO_YMINTERVAL(‘01-02') AS LEASE_PERIOD FROM DUAL; The output is: SYSDATE LEASE_PERIOD ------- ------------- 20-FEB-02 20-APR-03 In the above query, the current date is first retrieved. Then a period of one year and two months is added to it and displayed as lease period. © SQL Star International Ltd. 273
  • 277. TO_DSINTERVAL TO_DSINTERVAL converts a character string of CHAR, VARCHAR2, NCHAR or NVARCHAR2 datatype to an INTERVAL DAY TO SECOND type. The INTERVAL DAY TO SECOND datatype stores a period of time using the DAY and SECOND datetime fields. The format of the INTERVAL DAY TO SECOND is as follows: INTERVAL DAY [(day_precision)] TO SECOND Where, day_precision is the number of digits in the DAY datetime field. The default is 2. The syntax of TO_DSINTERVAL function is: TO_DSINTERVAL(char) Here, char is the string to be converted. To calculate a lease period that is fifty days, ten hours after current date, give the following query: SELECT SYSDATE,SYSDATE+TO_DSINTERVAL(‘50 10:00:00') AS LEASE_PERIOD FROM DUAL; The output is: SYSDATE LEASE_PERIOD ------- ------------ 29-MAY-07 18-JUL-07 In the above query, the current date is first retrieved. Then a period of fifty days, ten hours is added to it and displayed as lease period. TZ_OFFSET Every time zone across the globe has a corresponding offset. The TZ_OFFSET function returns the corresponding time zone of the value entered depending on the date when the statement is executed. For instance, if the return value of the TZ_OFFSET function is –5:00, it indicates that the time zone from where the statement was executed is five hours after UTC. If it is +2:00, the time zone is two hours ahead of UTC. The TZ_OFFSET function can take : A valid time zone name A time zone offset from UTC, (which returns itself) The keyword SESSIONTIMEZONE The keyword DBTIMEZONE © SQL Star International Ltd. 274
  • 278. The syntax of the TZ_OFFSET function is: TZ_OFFSET ([‗time_zone_name‘] [‗[+ | -] hh:mm‘] [SESSIONTIMEZONE] [DBTIMEZONE] To find out the time zone offsets of the regions America/Chicago and Asia/Singapore, give the following statements: SELECT TZ_OFFSET(‗America/Chicago‘) FROM DUAL; The output is: America/Chicago Time Zone is: TZ_OFFSET --------- -06:00 Asia/Singapore Time Zone is: SELECT TZ_OFFSET(‗Asia/Singapore‘) FROM DUAL; The output is: TZ_OFFS ------- +08:00 The return values indicate that America/Chicago time zone is six hours behind UTC and Asia/Singapore time zone is eight hours ahead of UTC. To find out the time zone offset of the current session, give the following statements: SELECT TZ_OFFSET(SESSIONTIMEZONE) FROM DUAL; The output is: TZ_OFFSET --------- +05:30 The session time zone is five and a half hours ahead of the UTC. To find out the time zone offset of the region where the database is installed, give the following statement: SELECT TZ_OFFSET(DBTIMEZONE) FROM DUAL; The output is: © SQL Star International Ltd. 275
  • 279. TZ_OFFS ------- -05:00 The database time zone is five hours behind the UTC. Modifying Table Structure Once a table has been created in the database, it does not necessarily mean that the table structure is permanent. It can also be modified depending on the need to do so. For example, the developer would have defined the length of the book name column as 20 at the time of creating the Book table. But, while attempting to insert the details of the book ‗The Strange Case Of Dr. Jekyll And Mr. Hyde‘, the Oracle server would generate an error as the length of the book name does not match the column length defined. This problem necessitates changing the column length. Apart from this, there can be various other instances where you may need to change the table structure. This brings into the picture the following changes that a table structure may undergo. Changing column definitions Adding new columns Changing the definitions of the existing columns Removing columns altogether Changing table definitions  Removing tables from the database  Renaming tables Manipulating Column Definitions After creating a table, you would need to change its structure if: A column has been omitted while creating the table The data being inserted into a column does not conform to the column definition An unwanted column has been added to the table at the time of its creation © SQL Star International Ltd. 276
  • 280. Column definitions can be manipulated using the ALTER TABLE statement. The ALTER TABLE Statement The ALTER TABLE statement is used to: Add new columns Modify existing columns Remove columns Mark columns as unused Adding Columns At the time of creating tables, only those columns that are considered to be important are created. But at a later stage, new columns may need to be added to the table. Using the ALTER TABLE statement with the ADD clause can help. The syntax for adding a column is, ALTER TABLE <table_name> ADD (column datatype [DEFAULT expr] [, column datatype]…); Where, table_name is the name of the table column is the name of the column to be added datatype is the datatype and the width of the new column DEFAULT expr is the default value that may be specified for the new column For example, at the time of creating the Member table, the developer may have omitted the creation of a column to store the email IDs of members. But later, due to the wide usage of email facilities, he decides to add a column to store email IDs of members. The database developer can add this additional column by using the ALTER TABLE statement. ALTER TABLE Member ADD (cEmailID CHAR (50)); When the table is altered successfully you will see the following message. Table altered. Points to remember © SQL Star International Ltd. 277
  • 281. While adding a new column, you cannot specify where it is to appear in the table. The new column is always the last column. A new column added to a table (already containing rows of data) is initially NULL for all the rows. If a column with NOT NULL constraint is to be added, then: 1 The column must first be added to the table without the constraint. 2 It must be populated with data in all the rows. 3. Once the column values are not null, the NOT NULL constraint can be added to it. In a table, only one column can be of LONG and LONG RAW datatype. Therefore, you cannot add columns of LONG and LONG RAW datatypes if the table already has columns of these datatypes. Modifying Columns While creating tables, columns are defined along with their datatypes and lengths in order to identify the type of data that the columns can hold. In case you want to alter the column to hold values larger than the current ones then the new column length must be made larger. This can be done by using the ALTER TABLE statement with the MODIFY clause. The syntax for modifying a column is: ALTER TABLE <table_name> MODIFY [column datatype [DEFAULT expr] [, column datatype]…); For example, in the Book table, the column cBookName is defined of length 20. But, while attempting to enter details of book ‗The strange case of Dr. Jekyll and Mr. Hyde‘, the Oracle server would generate an error because the book name happens to be longer than the length defined for the column. Therefore, modify the column width so as to accommodate long book names. ALTER TABLE Book MODIFY (cBookName CHAR (100)); In the code, the length of the cBookName column has been changed from 20 to 100. In addition to changing the column length, the column datatype and default value can also be changed. Points to remember:  © SQL Star International Ltd. 278
  • 282. Increasing column length using the MODIFY clause is OK, but decreasing them or changing the column datatype tends to be tricky. For example, if the column length of cMemberID were reduced from 9 to 7, then all those members having IDs of lengths more than 7 would not satisfy the column definition and would therefore get truncated. ALTER TABLE Member MODIFY cMemberID CHAR (7); ERROR at line 2: ORA-01441: column to be modified must be empty to decrease column length In order to overcome this problem, some special steps need to be taken.  Before reducing the column length, ensure that the column has all null values. But before deleting all the values from the column in question, create a temporary table to store the values of the column. This can be done by using the CREATE TABLE AS SELECT statement, where the SELECT statement extracts data from the primary key column and the column that is to be modified. Changing the DEFAULT value of a column affects only succeeding insertions to the column. Dropping Columns Columns are dropped when you no longer need them from a table. The DROP COLUMN clause with the ALTER TABLE statement is used to remove a column. This feature is available only from Oracle8i. The syntax for dropping columns is, ALTER TABLE <table_name> DROP COLUMN <column_name>; Where, <column_name> specifies the column that is to be dropped. For example, the developer creates the Category table with the following columns: cCategoryID  cCategoryCode  cCategoryName CREATE TABLE Category (cCategoryID CHAR (5) PRIMARY KEY, cCategoryCode CHAR (4), © SQL Star International Ltd. 279
  • 283. cCategoryName CHAR (15) ); But after creating the table, the developer realizes that both the cCategoryID and cCategoryCode columns hold the unique identity numbers given to each category. Therefore, one of them must be removed from the table structure. This can be done using the DROP clause as follows: ALTER TABLE Category DROP COLUMN cCategoryCode; Points to remember The dropped column may or may not contain data. At a time only one column can be dropped. The table must have at least one column left after one of its columns has been dropped. A dropped column cannot be recovered. Mark Columns as UNUSED The database developers or administrators could feel that some columns in a table are not appropriate or not required to be included in the table. Therefore, they would decide to drop these columns from their respective tables. But the response time taken for executing a DROP clause is quite slow. This is because dropping of columns using the DROP clause results in the restoration of the storage disk space. Also, dropping of columns could come in the way of any transaction that is currently accessing the database and system resources. © SQL Star International Ltd. 280
  • 284. Therefore, to speed up the response time you could mark the columns to be dropped as unused. Doing so does not restore the disk space. Instead, the columns so marked could later be dropped when the requirement for the system resources is less. The option used to mark one or more columns as unused is the SET UNUSED option. The syntax to mark columns as unused is, ALTER TABLE <table_name> SET UNUSED (<column_name>); or, ALTER TABLE <table_name> SET UNUSED COLUMN <column_name>; Where, SET UNUSED COLUMN are the keywords to mark the column table_name is the table name column_name is the column name For example, the New Jersey Central Library decides to drop the cMaritalStatus column from the Member table. But the database developer or administrator considers the option of dropping the column during the library hours as not advisable. This is because the act of dropping the column could come in the way of users accessing the table. Therefore, they decide to mark it as unused and drop it probably after library hours when the demand on the resource is less. ALTER TABLE Member SET UNUSED (cMaritalStatus); Table altered. On marking cMaritalStatus as unused, it is treated as if it were dropped. But on marking it as unused: Its values are not removed from each row in the table. Meaning that the disk space used by it is not restored. As the disk space is not restored, the response time is faster when executing the SET UNUSED option. © SQL Star International Ltd. 281
  • 285.  Though the column data remains in the table‘s rows, you cannot access it by using the ‗SELECT *‘ query. Also, the column will not be displayed even by issuing the DESCRIBE command. SELECT cMemberID,cBranchID,cMaritalStatus FROM Member; Displays the following error message: SELECT cMemberID,cBranchID,cMaritalStatus * ERROR at line 1: ORA-00904: invalid column name It will also not be displayed when you describe the structure of the table. DESCRIBE Member Name Null? Type -------- --------- ------- CMEMBERID NOT NULL CHAR(9) CFIRSTNAME NOT NULL CHAR(20) CLASTNAME NOT NULL CHAR(20) VADDRESS NOT NULL VARCHAR2(50) CAREA NOT NULL CHAR(10) CZIPCODE NOT NULL CHAR(7) CPHONE CHAR(10) NAGE NUMBER(2) DMEMBERSHIPDT DATE CGRADE CHAR(1) CBRANCHID CHAR(7) A new column with the same name as the unused column can be added to the table. ALTER TABLE Member ADD cMaritalStatus CHAR (1); The disk space occupied by cMaritalStatus column, which is marked unused cannot be restored. However, if you want to reclaim the disk space, you can drop the © SQL Star International Ltd. 282
  • 286. unused column. Use the DROP UNUSED COLUMNS option to do this. The syntax for the same is: ALTER TABLE <table_name> DROP UNUSED COLUMNS; To drop the unused column from Member table:- ALTER TABLE Member DROP UNUSED COLUMNS; This statement removes the marked column from the Member table. However, if you would have dropped the cMaritalStatus column using the DROP clause, then  The disk space used by the column is restored. This means that values of cMaritalStatus are removed from each row in the table and the space occupied by it is now available for any further use.  As the disk space has to be restored, the response time taken by executing the DROP COLUMN clause is slower.  The data stored in cMaritalStatus is lost and cannot be recovered.  Executing a ‗SELECT *‘ query will not retrieve data from cMaritalStatus. Manipulating Table Definitions There may arise circumstances when you would have to make major modifications to the database. These modifications could be related to changing or removing the definition of a table, such as: Giving the table a new name Truncating a table i.e. deleting rows without affecting its definition Dropping the table altogether © SQL Star International Ltd. 283
  • 287. These modifications are done using DDL commands. Dropping Tables If the basic need of a database changes, then you would have to make some changes to the tables created within the database. In order to drop a table, the DROP TABLE command is used. Its syntax is: DROP TABLE <table_name>; Where, table_name is the table that is to be dropped. In case you want to delete the Member table issue the following command. DROP TABLE MEMBER; A point to remember is that dropping tables is not simple. Before issuing the DROP TABLE command ensure that no other table references the table to be dropped. In other words, there should be no foreign key columns referencing the table. In case you go ahead and issue the command you will see the following error message. ORA-02449: unique/primary keys in table referenced by foreign keys To overcome this you must use the CASCADE CONSTRAINTS clause with the DROP TABLE command. Using this clause drops the constraints that refer to the table being dropped. In the above example, the Member table has a primary key constraint that is being referenced by a foreign key constraint of Transaction table. Therefore, to overcome this error use the CASCADE CONSTRAINTS clause as follows: DROP TABLE Member CASCADE CONSTRAINTS; The code executed is irreversible. This is because the DROP command is a DDL command. You can confirm this by trying to rollback the statement. When you issue the ROLLBACK command you get the following message: Rollback complete. This message implies that the rollback activity has been completed. Issue the DESCRIBE command to check if the table still exists. On doing so the following message is displayed: ORA-04043: object Member does not exist Points to remember while using the DROP TABLE command: The table definition is removed from the database Data stored within the table is deleted © SQL Star International Ltd. 284
  • 288.  You cannot roll back the DROP TABLE command. Being a DDL command it is auto commit by nature. Flashback Table A table can be reinstated automatically using a new 10g feature referred to as Flashback table feature. Here is a scenario that happens more often: A user drops a very important table accidentally, and it needs to be recovered as soon as possible. Use the Flashback Table feature, which makes the recovery of a dropped table as easy as the execution of a few statements. Let‘s see with an example, how this feature works. Drop the Member table of the library application SQL> DROP TABLE Member; Displays: Table dropped. Let‘s check the status of the table now. SQL> SELECT * FROM tab; TNAME TABTYPE CLUSTERID ----------------------------- ---------- ---------- cpndanfgMAAAAAANPw==$0 TABLE The table Member is gone but note the presence of the new table BIN$04LhcpndanfgMAAAAAANPw==$0. Here‘s what happened: The dropped table Member, instead of completely disappearing, was renamed to a system-defined name. It stays with the same structure as that of the original table. If there are indexes defined on the table, they are renamed too, using the same naming convention used by the table. The table and its associated objects are placed in a logical container known as the ―Recycle Bin,‖ which is similar to the one we have in our PC. The Recycle Bin is merely a logical structure that catalogs the dropped objects. Use the following steps to restore the dropped table back. SQL> SHOW RECYCLEBIN ORIGINAL-NAME RECYCLEBIN-NAME OBJECT- DROP TIME TYPE © SQL Star International Ltd. 285
  • 289. ------------- ----------------------------- ------- ------------------- RECYCLETEST BIN$04LhcpndanfgMAAAAAANPw==$0 TABLE 2007-05- 19:16:31:10 This shows the original name of the table, RECYCLETEST, as well as the new name in the Recycle Bin, which has the same name as the new table we saw created after dropping the table. (Note: The internal Name given may be OS dependent) To reinstate the table, all you have to do is use the FLASHBACK TABLE command: SQL> FLASHBACK TABLE Member TO BEFORE DROP; FLASHBACK COMPLETE. SQL> SELECT * FROM TAB; TNAME TABTYPE CLUSTERID -------------- ----------- ----------- MEMBER TABLE But what if you want to drop the table completely, without needing a flashback feature. In that case, you can drop it permanently using: DROP TABLE MEMBER PURGE; This command will not rename the table to the Recycle Bin name, rather, it will be deleted permanently, as it would have been pre-10g. Managing the Recycle Bin PURGE TABLE Member; Or using its Recycle Bin name: PURGE TABLE ―BIN$04LhcpndanfgMAAAAAANPw==$0‖; This command will remove table MEMBER and all dependent objects such as indexes, constraints, and so on from the recycle bin, saving some space. If, however, you want to permanently drop an index from the recycle bin, you can do so using: PURGE INDEX in_Member_01; This will remove the index only, leaving the copy of the table in the recycle bin. Truncating Tables The TRUNCATE TABLE statement is a part of the Data Definition Language that performs high-speed data deletion. The TRUNCATE statement deletes data from tables just as the DELETE statement, but with a slight difference. The difference being in the speed with which the deletion is performed by the two statements. The DELETE statement uses the transaction processing control commands for the completion of its task. That is, the task performed by a DELETE statement is not considered to be complete unless the task is committed to the database. This makes © SQL Star International Ltd. 286
  • 290. it a very slow process. Therefore, using the DELETE statement proves to be an inefficient option when the task is to remove data from a large table. On the other hand, the TRUNCATE statement bypasses the transaction processing control commands because the task gets automatically committing on execution of the statement. If a user were sure that he or she wants to delete a large number of rows from a table, then using the DELETE option would prove to be time consuming. Therefore, executing the TRUNCATE statement immediately deletes all rows from a table releasing the storage space occupied by them. This is the reason why the TRUNCATE statement is known as the high-speed data deletion statement. The syntax for truncating a table is: TRUNCATE TABLE <table_name>; Truncate the Member table from the library database SQL>TRUNCATE TABLE Member; This statement removes all row data from the Member table. Points to remember while using the TRUNCATE statement:   Data from all rows are deleted, but the table definition including the definition of constraints remains intact.  The storage space occupied by all rows is released.  As it is a DDL statement, data once deleted cannot be recovered. Changing Table Names At times you might have to change the names of tables in case they have not been named according to the naming conventions of the organization or if a newly created table is to be given a name as that of an already existing table. You can change the name of a table with the RENAME statement. Its syntax is: RENAME <old_name> TO <new_name>; Where, old_name is the old name of the table. © SQL Star International Ltd. 287
  • 291. new_name is the new name with which it is to be replaced. You created a table Publisher to store details of publishers. You want to make the name more self-explanatory and want to change it to PublisherDetails. In order to this, issue the following statement: SQL> RENAME Publisher TO PublisherDetails; In the example, the RENAME statement changes the name of the Publisher table to PublisherDetails. The message displayed is: Table renamed. Data Dictionary Tables The tables you have worked with, were all created and maintained by developers such as yourself. But in addition to these tables, Oracle server provides tables that are not created by developers. They are known as Data Dictionary tables. More discussion on this will be done separately later. © SQL Star International Ltd. 288
  • 292. Summary In this chapter, you have learnt that:  Data Definition commands (DDL) are used to create and manage database objects in a schema.  Schema is a collection of database object. The word SCHEMA and USER are interchangeable.  DDL commands are CREATE: creates new database object, ALTER: modify the structure of the database object, DROP: removes the database object from the schema, RENAME: gives a new name to the database object, TRUNCATE: removes rows permanently leaving the structure intact .  New tables can be created using an existing table using a subquery in the CREATE TABLE statements.  Datatypes such as VARCHAR2, CHAR, NUMBER, DATA and various TIMESTAMP determine the type of data a column can hold.  FLASHBACK statement can be used to restore the dropped objects.  Dropped objects of a schema can be viewed using SHOW RECYCLE BIN command.  Table can be removed from the recycle bin using PURGE command. © SQL Star International Ltd. 289
  • 293. Lab Exercise 1. Create a table Dept_details based on the details given in the following chart. Save the syntax in a script named LabEx12_01.sql. Execute the script and confirm that the table has been created. 2. Populate the Dept_details table with data from Departments table. Insert only the columns that you need. 3. Create a table Emp_details based on the following chart. © SQL Star International Ltd. 290
  • 294.  4.  Modify the empFirstName and empLastName columns in the Emp_details table to allow for longer names. Table altered. 5. Create a table emp2 based on the structure of employees table. Include the columns employee_id, first_name, last_name, department_id, job_id, and salary into the Emp2 table. 6. Drop the Emp_details table. 7. Rename the table Emp2 as Emp_details. 8. Drop the column first_name from the table Emp_details and see the structure of the table © SQL Star International Ltd. 291
  • 295. . Make the job_id column of Emp_details table UNUSED and confirm the modification. 10 Drop all the unused columns from Emp_details table, confirm the modification.  11.Create a table New_Emp having employee details, and hire date as TIMESTAMP datatype. 12. Modify the table New_Emp with hiredate as TIMESTAMP WITH TIMEZONE datatype. View the structure of the table. 13. Try the following: a) Create table test with column specified below: x NUMBER b) Select all the tables from present schema. c) Drop the Test table from schema. d) Select all the tables from current schema and see the change. e) Display the contents of RecyleBin f) Write the command to reinstate the table. © SQL Star International Ltd. 292
  • 296. g) Select all the tables from current schema. h) Drop the table completely without flashback feature or drop it permanently. i) What command is used to remove the table from Recycle Bin after the table is dropped. © SQL Star International Ltd. 293
  • 297. Chapter 13 Managing Constraints Introduction to Constraints Defining Constraints at different level Explain the different types of Constraints Creating Constraints Deferring Constraints Dropping Constraints Enabling and Disabling the Constraints Querying Data Dictionary for Constraints © SQL Star International Ltd. 294
  • 298. Objectives At the end of this chapter, you will be able to:  Understand Integrity constraints  Maintain Integrity constraints  Understand Deferred Constraints  Understand Dictionaries related to constraints © SQL Star International Ltd. 295
  • 299. Enforce Business Rule In any organization, Data plays an important role in its day to day functioning. In order to prevent entry of invalid data into tables, Oracle server uses a mechanism called constraints. Constraints (also known as data integrity constraints) are mainly used to enforce business rules. They ensure accuracy and consistency of data in a relational database. Referential Integrity Constraints therefore ensure that: Inserting, updating and deleting of rows from a table succeed only if the constraints are satisfied.  Parent tables (those tables on which other tables are dependent) are not deleted. Defining Constraints Constraints can be defined before or after the table creation. There are two levels for defining a constraint:  Column level  Table level Column Level Constraints Column level constraints are defined within the column specification and reference only a single column. Hence, they enforce restriction on the type of data that can be entered into that column. The syntax is: CREATE TABLE <table_name> <column_name> datatype,. . . [CONSTRAINT <constraint_name>] <constraint_type>,…. Where, column_name is the name of the column for which the constraint is to be defined. datatype specifies the type of data that can be entered into the column. CONSTRAINT constraint_name assigns a name to the constraint that is being defined for the column. This clause is not mandatory. constraint_type specifies the type of constraint being defined. Different constraint types are covered next. © SQL Star International Ltd. 296
  • 300. Table Level Constraints Table level constraints are defined separately from the column specifications and can reference one or more columns. They enforce restrictions on the type of data that can be entered into the table. All constraints except NOT NULL can be defined at this level. The syntax is: CREATE TABLE <table_name> <column_name> datatype,. . . [CONSTRAINT <constraint_name>] <constraint_type> (column, ….) Where, constraint_name is name of the constraint. constraint_type is the type of constraint. Types of Constraints The data integrity constraints used to enforce business rules are: NOT NULL: This constraint prevents null values from being entered into a column. UNIQUE: This constraint ensures that the column values or combination of column values is unique for all rows in the table.  PRIMARY KEY: This constraint prevents null values into the column and identifies each row of a table uniquely.    FOREIGN KEY: A foreign key constraint establishes a parent-child relationship by ensuring that the child column © SQL Star International Ltd. 297
  • 301. referencing the parent column has same values or are null. CHECK: A Check constraint checks whether a particular condition is met or not. The NOT NULL Constraint The NOT NULL constraint ensures that null values are prevented from being entered into columns. There can be instance, where some columns in a table can not have null values. For example, when a person registers himself as a member, the librarian must necessarily fill in his name, address and age in the Member table. This is because they are all vital pieces of information that cannot be done away with. Therefore, by defining these columns as NOT NULL, you ensure that null values are not entered into them. Create the Member table with constraints to prevent null values from being entered into member‘s name, address and age. CREATE TABLE Member (cMemberID CHAR (9), cFirstName CHAR (20) NOT NULL, cLastName CHAR (20) NOT NULL, vAddress VARCHAR2 (50) NOT NULL, cArea CHAR (10) NOT NULL, cZipcode CHAR (7) NOT NULL, cPhone CHAR (10), nAge NUMBER (2) NOT NULL, dMembershipDt DATE DEFAULT SYSDATE, cGrade CHAR (1), cBranchID CHAR(7) ); In the above code, all the NOT NULL constraints are defined at the column level. Since the constraints are unnamed, the Oracle server will generate names for them. You can however name the constraints while defining them along with the column specification as follows: CFirstName CHAR (20) CONSTRAINT MemberFNameNN NOT NULL, The UNIQUE KEY Constraint © SQL Star International Ltd. 298
  • 302. A UNIQUE KEY constraint ensures that no two rows of a table have identical values in a column or a collection of columns. UNIQUE KEY constraints allow the entry of null values unless NOT NULL constraint is defined for the same column. A UNIQUE KEY can be defined at the column level or table level. How would you ensure that two rows of the Branch table do not have the details of the same branch? You could do so with the following DDL statement. CREATE TABLE Branch (cBranchID NUMBER (7), cBranchName CHAR (25) CONSTRAINT BranchNameUK UNIQUE, vBranchAdress VARCHAR2 (50), cBranchLocation CHAR (15), cPhone CHAR (10), dEstbl DATE ); In the code, the cBranchName column has been defined as UNIQUE specifying that the column cannot have duplicate branch names. This is a column level constraint definition. A UNIQUE constraint is defined at the table level, usually if it comprises a collection of columns. A UNIQUE KEY constraint defined for a group of columns is known as a composite unique key. It ensures that the combinations of values in the columns are unique. To define a composite UNIQUE KEY constraint on the Book table to ensure that the book name and the publishing year of each book are unique, create the Book table in the following manner. CREATE TABLE Book (cBookID CHAR (13), cBookName CHAR (20) NOT NULL, cAuthorName CHAR (30) NOT NULL, cCategoryID CHAR (5), cPublisherID CHAR (6), dPublishedYr DATE, cBranchID CHAR (7), nNoOfCopies NUMBER (2), CONSTRAINT BkNamePublishYrUK UNIQUE (cBookName, dPublishedYr) ); © SQL Star International Ltd. 299
  • 303. The PRIMARY KEY Constraint A PRIMARY KEY constraint on a column or a collection of columns helps to uniquely identify each row in a table. A PRIMARY KEY constraint defined for a collection of columns is known as a Composite Primary key. The primary key constraint ensures that any value entered in the columns that is part of the primary key constraint must be unique for all rows. And they must not contain null values. Suppose the library desk officer wants to retrieve the details of a member named ‗Perry Paine‘. He would issue the following SELECT statement. SELECT * FROM Member WHERE cFirstName=‗Perry‘ AND cLastName=‗Paine‘; But, if the library has more than one member with the name ‗Perry Paine‘, how would the Oracle server be able to distinguish between them? This can be achieved by giving each member a distinct identity number so that they could be identified uniquely. This is achieved by defining the PRIMARY KEY constraint. PRIMARY KEY constraints can be defined at the column level or at the table level. To define PRIMARY KEY constraint at the column level for the Member table. CREATE TABLE Member (cMemberID CHAR (9) CONSTRAINT MemID_PK PRIMARY KEY, cFirstName CHAR (20) NOT NULL, cLastName CHAR (20) NOT NULL, vAddress VARCHAR2 (50) NOT NULL, cArea CHAR (10) NOT NULL, cZipcode CHAR (7) NOT NULL, cPhone CHAR (10), nAge NUMBER (2) NOT NULL, dMembershipDt DATE, cGrade CHAR (1), cBranchID CHAR(7)); © SQL Star International Ltd. 300
  • 304. In the code, the PRIMARY KEY is defined at the column level for the column cMemberID. This constraint ensures that, when a row is inserted in the Member table, the value for cMemberID column is a non-null value and is not same as an existing column value of another row. The FOREIGN KEY Constraint A FOREIGN KEY constraint is defined on the column of a child table, which is dependent on the primary key column of the parent table. Defining a FOREIGN KEY constraint on a column or a collection of columns establishes a relationship between the foreign key columns and the primary key or unique key columns of the same table or a different table. This constraint ensures that foreign key columns do not contain values that do not exist in the primary key column, they are referencing. FOREIGN KEY constraints can be defined at the column level or at the table level. The foreign key constraint is defined at the table level using the following keywords: FOREIGN KEY specifies the foreign key column in the child table. REFERENCES identifies the column in the parent table that the foreign key column is dependent on. ONDELETE CASCADE indicates that when a row in the parent table has been deleted, its dependent rows in the child table are also deleted.  ON DELETE SET NULL converts foreign key values to null when parent value is removed. But, without the ON DELETE CASCADE and ON DELETE SET NULL, you cannot delete rows from the parent table if there are dependent rows in the child table. For example, there exists a parent-child relationship between the Book table and the Transaction table. The Transaction table contains the issue details of those books that are listed in the Book table. The foreign key constraint is defined on the cBookID column of the Transaction table (child table or dependent table). It refers to the cBookID column of the Book table (parent or referenced table), which is the primary key column. To ensure that the books issued to members are those that are available in the Book table of the library, create the Transaction table as follows: © SQL Star International Ltd. 301
  • 305. CREATE TABLE Transaction (cTranID CHAR(11) CONSTRAINT TransactionTranIDPK PRIMARY KEY, cMemberID CHAR(7), cBookID CHAR(13), dIssueDt DATE, dReturnDt DATE, dActualReturnDt DATE, nFine NUMBER(2), CONSTRAINT TransactionBookIDFK FOREIGN KEY(cBookID) REFERENCES Book(cBookID)ON DELETE CASCADE, CONSTRAINT TransactionMemberIDFK FOREIGN KEY(cMemberID) REFERENCES Member(cMemberID)ON DELETE CASCADE); When the FOREIGN KEY constraint is defined at the column level, there is a slight change in the syntax. The FOREIGN KEY keyword is not used while defining it. The following example illustrates this: Define a constraint on the Availability table to ensure that it stores the status of availability of only those books that are stored in the library. CREATE TABLE Availability (cBookID CHAR(13) CONSTRAINT AvailabilityBookIDFK REFERENCES Book (cBookID), nAvailableCopies NUMBER (2), cBranchID CHAR (7) CONSTRAINT AvailabilityBranchIDFK REFERENCES Branch (cBranchID)); In the code, the FOREIGN KEY constraint has been defined at the column level for both cBookID column and cBranchID column. © SQL Star International Ltd. 302
  • 306. The CHECK Constraint The CHECK constraint ensures that the data being entered into a column satisfies a set of valid values or conditions. For instance, it is the New Jersey Central Library‘s policy not to allow any person below the age of five to be registered as its member. Hence, if the librarian inserts a row into the Member table entering a member‘s age as four, then the Oracle server would return an error saying that the CHECK constraint for the nAge column has been violated. To check whether the age of persons being entered in the Member table is not below five, issue the constraint as follows: CREATE TABLE Member (cMemberID CHAR (9) CONSTRAINT MemberMemberIDPK PRIMARY KEY, cFirstName CHAR (20) NOT NULL, cLastName CHAR (20) NOT NULL, vAddress VARCHAR2 (50) NOT NULL, cArea CHAR (10) NOT NULL, cZipcode CHAR (7) NOT NULL, cPhone CHAR (10), nAge NUMBER (2) CONSTRAINT MemberAgeCK CHECK (nAge >5) NOT NULL, dMembershipDt DATE DEFAULT SYSDATE, cGrade CHAR (1) cBranchID CHAR(7) REFERRENCES Branch(cBranchID)); In the code, the CHECK constraint is defined for the nAge column, which ensures that the age being entered is not below five. Points to remember:  While defining CHECK constraints, reference to columns or rows of any table, including the one on which the constraint has been defined cannot be made. For example, to check whether the publisher IDs entered in the Book table is among the publisher IDs specified in the PublisherDetails table you would type: CREATE TABLE Book (cBookID CHAR(13) CONSTRAINT BookBookIDPK PRIMARY KEY , cBookName CHAR(20) NOT NULL, © SQL Star International Ltd. 303
  • 307. cAuthorName CHAR(30) NOT NULL, cCategoryID CHAR(5) CONSTRAINT BookCategoryIDFK REFERENCES Category(cCategoryID) , cPublisherID CHAR(6) CHECK (cPublisherID IN (SELECT cPublisherID FROM Publisher)), dPublishedYr DATE,cBranchID CHAR(7)CONSTRAINT BookBranchIDFK REFERENCES Branch(cBranchID), nNoOfCopies NUMBER(2) CONSTRAINT BookNoOfCopiesCK CHECK(nNoOfCopies < 11)); However, this code is not valid as it refers to the cPublishedID column of the PublisherDetails table and it displays the following error message: ORA-02251: subquery not allowed here References to functions such as SYSDATE, USER, etc. cannot be made while defining a CHECK constraint. MultipleCHECK constraints can be defined for a single column. CHECK constraints can be defined at column level or table level. Execute the following code to check whether the number of copies of books entered in the Availability table is not more than 5. CREATE TABLE Availability (cBookID CHAR(13) CONSTRAINT AvailabilityBookIDFK REFERENCES Book (cBookID),nAvailableCopies NUMBER (2), cBranchID CHAR(7) CONSTRAINT AvailabilityBranchIDFK REFERENCES Branch(cBranchID), CONSTRAINT AvailabilityCopiesCK CHECK(nAvailableCopies < 5)); In the code, the CHECK constraint on nAvailableCopies column has been defined at the table level. © SQL Star International Ltd. 304
  • 308. Consider an example shown below: CREATE TABLE Emp ( Empcode NUMBER(6), Ename VARCHAR2(20)CONSTRAINT chk_ename CHECK(ename=UPPER(ename)), Job_ID VARCHAR2(10) NOT NULL, Email VARCHAR2(40) UNIQUE, CONSTRAINT empid_pk PRIMARY KEY (Empcode) ); In the above example empid_pk is a constraint defined as a primary key in the table level for the column empcode. The above example can be modified as: CREATE TABLE Emp ( Empcode NUMBER(6) CONSTRAINT empcd_pk PRIMARY KEY, Ename VARCHAR2(20), ... Job_ID VARCHAR2(10) NOT NULL © SQL Star International Ltd. 305
  • 309. ); Manipulating Tables using Constraints If there are changes to the business rules, then changes to the constraints that enforce these rules need to be made. These changes could include adding, removing, disabling or enabling constraints. Adding Constraints Even when business rules have not been finalized, the database developers create the tables so that, later the rules could be added to the columns or the tables of the database. The syntax for adding a constraint is, ALTER TABLE <table_name> ADD [CONSTRAINT <constraint_name>] constraint_type (<column_name>); Where, table_name is the name of the table constraint_name is the name of the constraint. The constraint name syntax is optional. constraint_type specifies the type of constraint to be added. column_name is the name of the column to which constraint is to be added. For instance, the library has not decided the rule pertaining to the eligibility of a person to be registered as a member. The developer still creates the Member table. Later, when the library management decides that only persons above the age of five should be enrolled as members, this rule could then be incorporated in the Member table which is already created. ALTER TABLE Member ADD CONSTRAINT MemberAgeCK CHECK (nAge < 5); By adding this constraint, only the subsequent ages entered after the addition of the constraint will be checked. Another case where you need to alter a constraint is to add a constraint to ensure that the grades allotted to each member in the Member table belongs to one of the grades decided upon on the basis of age range in the MemberFee table. ALTER TABLE Member © SQL Star International Ltd. 306
  • 310. ADD (CONSTRAINT MemberGradeFK FOREIGN KEY (cGrade) REFERENCES MemberFee (cGrade)); In the code, FOREIGN KEY constraint is added to establish a parent-child relation between the Member table and the MemberFee table by ensuring that the grade values in the Member table correspond to the grade values in the MemberFee table. Points to remember while adding constraints: The column to which the constraint is to be added must already exist in the table. PRIMARY KEY constraints: The columns must not have null values and must have only unique values. FOREIGN KEY constraints: The columns must have values corresponding to values in the referenced primary key column or be null. UNIQUE constraints: The column must have either unique values or be null. CHECK constraints: Apply only to the subsequent data added to the column. NOT NULL constraints: These constraints can only be defined at column level. NOT NULL constraints are added using the MODIFY clause in the ALTER TABLE statement. Deferred Constraints Normally, constraints are checked as data is inserted or updated in the row. When a row is inserted, all the constraints are checked and then, the row is either accepted or rejected. You can, however, defer the constraint checking until the transaction commits. In that case, the row is inserted into the table and constraints are not checked until the COMMIT is issued. If the row then fails, it is removed from the table. You can change the status of the constraints by setting them as DEFERRED or IMMEDIATE. In order to change the constraint, it must be set to DEFERRABLE. Consider an Example for using Deferred Constraints: CREATE TABLE Dupemp (Empno NUMBER(4) CONSTRAINT pk_empno PRIMARY KEY, Name VARCHAR2(20), Deptno NUMBER(2) © SQL Star International Ltd. 307
  • 311. ); CREATE TABLE Dupdept (Deptno NUMBER(2) CONSTRAINT dp_pk PRIMARY KEY, Dname VARCHAR2(20), Loc VARCHAR2(20)); If you try to enter values into Deptno column of Dupemp table, which does not lie within the domain of the column values of Dupdept table, an error message is thrown indicating the violation of foreign key constraint. But, if you still want to add data into the Dupemp table, you can do it by changing the status of the constraints by setting them as DEFERRED or IMMEDIATE. The advantage of doing this is it defers constraint checking until the transaction is committed. In order to change the constraint, it must be set to DEFERRABLE. ALTER TABLE Dupemp ADD CONSTRAINT dep_fk FOREIGN KEY(deptno) REFERENCES dupdept(deptno) ON DELETE CASCADE DEFERRABLE; SQL> SET CONSTRAINT dep_fk DEFERRED; Now, you insert values into detpno of Dupemp table directly without entering the corresponding deptno value in the main table. As an example, the above one works perfect. But, why at all we need a deferred constraint? Sometimes, it so happens that, we get the data for the secondary table, but not for the main table. Since there is a referential integrity constraint present on these two tables, we cannot enter data directly into the second table. By deferring the foreign key constraints, we can atleast get the data loaded into the secondary tables, and then validate the data against the main table once it is also loaded. This saves time. When a COMMIT statement is issued against the secondary table, constraints are checked and invalid data is rejected. We can enable the deferred constraint by issuing the following command: SQL> SET CONSTRAINTS dep_fk IMMEDIATE; Dropping Constraints If the organization decides to do away with a business rule, then you will have to drop the constraint that enforced the rule. Use the DROP clause with the ALTER TABLE statement to remove a constraint. The syntax for dropping a constraint is: © SQL Star International Ltd. 308
  • 312. ALTER TABLE <table_name> DROP PRIMARY KEY | UNIQUE (column_name)| CONSTRAINT constraint_name [CASCADE]; Where, PRIMARY KEY | UNIQUE (column_name)| specifies the primary key or the unique key columns of a table that are to be dropped. CASCADE option causes the dependent constraints to be dropped when the primary key or unique key constraints are dropped. Drop the primary key constraint from the Book table along with its associated foreign keys. ALTER TABLE Book DROP PRIMARY KEY CASCADE; In the code, the CASCADE option used with the DROP clause causes the dependent constraint on cBookID columns of Transaction table and Availability table also to be dropped. Enabling and Disabling Constraints Rectifying a constraint failed during creation is similar to the way any electric gadget would be repaired. To repair an electric gadget you would first of all see to it that the electric supply has been switched off until the repair work has been completed. Likewise, to repair a failed constraint you must first switch off or in technical terms disable the constraint and after taking steps to rectify the failure, switch on or enable it. Disabling Constraints The Oracle server automatically disables a constraint that has failed during creation. A simple example to explain this task. Create two tables Tab1 and Tab2. CREATE TABLE TAB1 (nCol1 NUMBER (4) CONSTRAINT TAB1nCol1PK PRIMARY KEY, cCol2 CHAR (4)); CREATE TABLE TAB2 (cColA CHAR (4),nCol1 NUMBER (4) CONSTRAINT TAB2nCol1FK REFERENCES TAB1 (cCol2)); © SQL Star International Ltd. 309
  • 313. In the above codes, the primary key constraint is defined on the column nCol1 of Tab1. The foreign key constraint is defined on the column nCol1 of Tab2. But the creation of this constraint fails as it references cCol2 of table Tab1 instead of nCol1. This automatically disables the Tab2nCol1FK constraint. The error message displayed is as follows: ORA-02267: column type incompatible with referenced column type In the above case, the constraint was disabled automatically as its creation failed. However, you can disable the constraint without dropping or re-creating it if you do not want to enforce the rules defined for it. Using the DISABLE clause with the ALTER TABLE statement can disable a constraint. Disabling a constraint renders it ineffective, as if it had been dropped. The syntax for disabling a constraint is: ALTER TABLE <table_name> DISABLE CONSTRAINT <constraint_name> [CASCADE]; Where, table_name is the table name constraint_name is the constraint name CASCADE option disables a dependent constraint if its primary key constraint is disabled. For example you can disable the unique key constraint defined on cBranchName column of the Branch table. ALTER TABLE Branch DISABLE CONSTRAINT BranchBranchNameUK; In this example you did not have to issue the CASCADE clause because the disabled constraint did not have any dependent constraints. An example where you will have to issue the CASCADE clause is to disable the primary key constraint defined on the cBookID column of the Book table. ALTER TABLE Book DISABLE CONSTRAINT BookBookIDPK CASCADE; This example uses the CASCADE clause because disabling the constraint on cBookID column will affect the cBookID column constraint of the Transaction table. © SQL Star International Ltd. 310
  • 314. Points to remember: You can use the DISABLE clause with both the CREATE TABLE as well as the ALTER TABLE statements. Ensure that data being entered, while disabling of a constraint, does not violate the rule that had been defined. If such a precaution is not taken, then enabling the constraints later will not be a smooth process. Enabling Constraints You must enable the disabled constraints after you have taken the steps needed to correct the reasons that led to the failure of constraints during their creation. When constraints are enabled the business rules that were defined would be enforced. The syntax for enabling constraints is: ALTER TABLE <table_name> ENABLE CONSTRAINT <constraint_name>; Where, table_name is the table name constraint_name is the constraint name Points to remember: You can enable only those constraints which have been defined and which are currently disabled. When you attempt to enable a disabled constraint, ensure that the data that had been loaded into the table does not violate the rule that had been defined. This is because when you enable a constraint, that constraint applies to all the data in the table.  You can use the ENABLE clause with both the CREATE TABLE as well as the ALTER TABLE statements. The disabled UNIQUE KEY constraint of the Branch table can be enabled as follows: ALTER TABLE Branch ENABLE CONSTRAINT BranchBranchNameUK; In this code, the disabled unique constraint is enabled. But, if duplicate branch names had been entered during the time the constraint was disabled, then the above code would not execute and would display the following error: © SQL Star International Ltd. 311
  • 315. ORA-0229: cannot enable constraint BranchNameUK – duplicate keys found To enable the primary key constraint defined on the cBookID column of the Book table, execute the following statement: ALTER TABLE Book ENABLE CONSTRAINT BookBookIDPK; In this code, the disabled primary key constraint is enabled. But, if duplicate book IDs or null values had been entered during the time the constraint was disabled, then the above code would not execute and would display the following error: ORA-02298: cannot enable constraint BookBookIDPK –parent keys not found Cascading Constraints While dropping columns you need to handle, The referential integrity constraints that depend on the primary key or unique key constraints defined on the columns that are to be dropped. All multicolumn (a single constraint which defines rules for two or more columns) constraints defined on the columns that are to be dropped. Example of a multicolumn constraint is: CONSTRAINT Constraintname CHECK (Col1 > 10 AND Col2 = 25) The above-mentioned issues are handled by using the CASCADE CONSTRAINTS clause along with the DROP COLUMN clause in the ALTER TABLE statement. Its syntax is: ALTER TABLE <table_name> DROP COLUMN (<column_name>) CASCADE CONSTRAINTS; For example create a table TabA. CREATE TABLE TabA (nC1 NUMBER (4)PRIMARY KEY, nC2 NUMBER(3), nC3 NUMBER (3), © SQL Star International Ltd. 312
  • 316. nC4 NUMBER (4), CONSTRAINT TabAnC4FK FOREIGN KEY (nC4) REFERENCES TabA (nC1), CONSTRAINT TabACK1 CHECK (nC3 > 10 AND nC2 <5)); The table TabA is created with four columns nC1, nC2, nC3 and nC4. Primary key constraint is defined on column nC1 which is referenced by the foreign key column nC4. A multicolumn CHECK constraint is defined on columns nC2 and nC3. When you attempt to drop the columns nC1 and nC3, you would encounter error messages. ALTER TABLE TabA DROP COLUMN (nC1); Executing this statement would give the following error: ORA-00904: invalid column name This is because nC1 is being referenced by nC4. If you drop column nC3 ALTER TABLE TabA DROP COLUMN nC3; Executing this statement would give the following error: ORA-12991: column is referenced in a multi-column constraint This is because nC3 is part of the multicolumn constraint. To avoid these errors, use the CASCADE CONSTRAINTS clause with the DROP COLUMN clause. Hence drop the columns as follows: ALTER TABLE TabA DROP COLUMN nC1 CASCADE CONSTRAINTS; ALTER TABLE TabA DROP COLUMN nC3 CASCADE CONSTRAINTS; If the columns referencing the constraints of the dropped columns are also dropped, then you need not use the CASCADE CONSTRAINTS clause with the DROP COLUMN clause. © SQL Star International Ltd. 313
  • 317. For instance in the same example you drop columns C1 and C4 without the CASCADE CONSTRAINTS clause. ALTER TABLE TabA DROP (nC1, nC4); Querying USER_CONSTRAINTS Data Dictionary View You can confirm the creation of a table by issuing the DESCRIBE command. But, except the NOT NULL constraint, the DESCRIBE command does not verify the existence of other constraints that were defined during the creation of the table. Therefore, you can query the USER_CONSTRAINTS dictionary view to confirm the creation of all the constraints on your table. Before you query USER_CONSTRAINTS, issue the DESCRIBE command to see all the columns that are available in it. DESC USER_CONSTRAINTS Now, query USER_CONSTRAINTS using the SELECT statement to display all the constraints defined on the Member table. SELECT CONSTRAINT_NAME,CONSTRAINT_TYPE,SEARCH_CONDITION FROM USER_CONSTRAINTS WHERE TABLE_NAME=‘MEMBER‘; Displays the output: CONSTRAINT_NAME CON SEARCH_CONDITION --------------- --------- ------------------------- SYS_C001297 C ―CFIRSTNAME‖ IS NOT NULL SYS_C001298 C ―CLASTNAME‖ IS NOT NULL SYS_C001299 C ―VADDRESS‖ IS NOT NULL SYS_C001300 C ―CAREA‖ IS NOT NULL SYS_C001301 C ―CZIPCODE‖ IS NOT NULL MEMBERAGECK C nAge > 5 MEMBERMEMBERIDPK P MEMBERGRADEFK R 8 rows selected. © SQL Star International Ltd. 314
  • 318. In the code, you are retrieving the name of the constraint, the type of constraint and the search conditions used with the check constraints. If the user has not named the constraints, then the query retrieves the names assigned by the server. In the type of constraints retrieved by the code, C stands for CHECK and NOT NULL, P for PRIMARY KEY, R for FOREIGN KEY and U for UNIQUE KEY. Querying USER_CONSTRAINTS does not retrieve the columns on which the constraints have been defined. In order to view the columns associated with the constraints use the USER_CONS_COLUMNS data dictionary view. This view is especially useful when system assigned constraints names have been retrieved by USER_CONSTRAINTS, because these names do not help in identifying the columns on which they have been defined. You can identify the columns associated with the constraints by viewing the USER_CONS_COLUMNS data dictionary view. The usage of USER_CONS_COLUMNS dictionary view is most widely felt when you have to drop constraints from a table. To drop a constraint, you need to identify the name of the constraint that is to be dropped. By viewing USER_CONS_COLUMNS dictionary view, you can identify the constraint names and columns on which they have been assigned and then use it in the DROP CONSTRAINT clause. Display the constraints along with columns on which they have been defined on the Member table. SELECT CONSTRAINT_NAME,COLUMN_NAME FROM USER_CONS_COLUMNS WHERE TABLE_NAME=‗MEMBER‘; Displays the output: CONSTRAINT_NAME COLUMN_NAME -------------- -------------- MEMBERAGECK NAGE MEMBERGRADEFK CGRADE MEMBERMEMBERIDPK CMEMBERID SYS_C001297 CFIRSTNAME © SQL Star International Ltd. 315
  • 319. SYS_C001298 CLASTNAME SYS_C001299 VADDRESS SYS_C001300 CAREA SYS_C001301 CZIPCODE 8 rows selected. Summary In this chapter, you have learnt that:  Data accuracy and consistency can be checked by creating constraints in database.  Constraint can be defined before or after the table creation. These are defined either at the table level(after defining all the columns) or at the column level(after each column).  The different types of constraints are: NON NULL: defined only at column level and prevents NULL values, UNIQUE: prevents duplicate values, PRIMARY KEY: prevents duplicate and NULL values, FOREIGN KEY: values referred by PRIMARY KEY domain columns only, CHECK: allows values based on a criteria.  You can defer the constraints till the transaction commits using DEFFERED statement.  Constraint can be either created, dropped, enabled or disabled using ALTER statements.  Information regarding Constraints can be viewed in USER_CONSTRAINTS and USER_CONS_COLUMNS data dictionary respectively. © SQL Star International Ltd. 316
  • 320. Lab Exercise 1. Add a table level PRIMARY KEY constraint to the new_emp table on the empID column. Name the constraint as emp_id_pk. [Hint: Use the ALTER TABLE command]. 2. Create a table NEW_DEPT with columns for department ID, department name and location ID. Create primary key constraint to the NEW_DEPT table using the deptID column. Name the constraint deptID_pk. 3. Add the column deptID to the NEW_EMP table. Add a foreign key constraint on the NEW_EMP table using the deptID column. This ensures that the employees are not assigned to a department that does not exist. Name the foreign key constraint as emp_dept_fk. 4. Confirm that the constraints are added by querying the USER_CONSTRAINTS view. ------------- 7 rows selected. 5. Create a table dept_Details based on the following details. 6. Create a table emp_details based on the following chart. © SQL Star International Ltd. 317
  • 321. A) Modify the emp_details table to add the foreign key on department id column. Also ensure that this constraint can be deferred. B) Make Necessary changes to make the constraint deferred. C) Insert 1 record into emp_details table first. D) Will it raise an error during inserting? If no, then why? E) Try to commit the inserted data. Is the data committed? If no, why? © SQL Star International Ltd. 318
  • 322. Chapter 14 Views What are Views Simple vs Complex Views Enforcing Constraints on Views Creating Complex Views Creating Inline Views Data Access from Views © SQL Star International Ltd. 319
  • 323. Objectives At the end of this chapter, you will able to:  Describe the need for different types of views  Use views © SQL Star International Ltd. 320
  • 324. What are Views? A view is defined as a database object that allows you to create a virtual table, which would contain data selected from a table or a collection of tables and presented in a distilled form to conceal complexity. The tables on which views are based are known as base tables or underlying tables. Views can be compared to windows; windows that only give you a glimpse of the world surrounding you, concealing all its complexities. For example, consider the view residents living in a tall building like Majestic Towers would get. When person P1, living on the first floor looks out of his window, he probably gets to see nearby buildings like a bank, a hospital and some people going on with their daily activities. But when person P2, living on the top floor looks out of his window, the view he gets would differ from that of person P1. For instance, in addition to the buildings and people, he could also get a glimpse of trains plying from a near by station. This shows that each window shows a different view of the same landscape surrounding Majestic Towers. Similarly, VIEWS too present different views of the same table to different users. What the residents get to view from their windows does not belong to them. Similarly, views too contain no data of their own. Views are just results of SELECT statements. Therefore, when users manipulate data from views it is similar to manipulating data from a table. Why Views? Views are widely used due to the following reasons:  Views provide security as they can restrict data being accessed by users. For example, to implement data security, the library may create a view that will allow the librarian to see only the details of the library‘s members, thus, preventing him from manipulating data pertaining to the books, or the membership fee structure of the library.  Views conceal data complexity by making complex queries simple. For example, retrieving data from two or more tables using a JOIN statement could prove to be very confusing for an end user. To simplify this complexity, you could create a view, which is a combination of two or more tables. For example, you could create a view by combining the Book, Category and PublisherDetails tables, thereby enabling the end user to make a simple query on the view without ever having to know that it is based on these three tables.  View definition remains unaffected despite any alteration to the structure of its base tables (except when the tables are dropped or the table columns selected by the view is altered). For example, if a view were made of two tables, selecting two columns from one table and three columns from the other, adding one more column to the first table would not affect the view definition. Therefore, any application that refers to the view also remains unaffected. © SQL Star International Ltd. 321
  • 325.  Data dictionary views are widely used as they prevent users from directly accessing the tables of the data dictionary. This is important due to the following reasons:  To safeguard data stored in the data dictionary tables. If users manipulate data dictionary tables it could result in loss of data or the table itself being removed, thus causing serious damage to the Oracle database, even rendering it completely ineffectual or unproductive.  Data stored within the data dictionary tables are hard to comprehend. Therefore, dictionary views help to condense data into something easily comprehensible and helpful. Simple Views Vs Complex Views Views can be classified into two types depending on the need for which they are to be created. They are:  Simple views  views Complex The basic differences between simple and complex views are:  Simple views are based on only one table whereas complex views are based on more than one table. For example, the database developer could create a simple view based on the Book table. Whereas, he could create a complex view to show the books that belong to each category by joining the Book table and the Category table.  Simple views allow DML operations to be performed (but with certain restrictions) whereas complex views do not always allow DML operations to be performed. The syntax for creating simple as well as complex view is the same except that the subquery that defines a simple view cannot have any join conditions or group functions. Creating Views To create a view, a subquery must be embedded within the CREATE VIEW statement. The syntax for creating a view is: CREATE [OR REPLACE] [FORCE| NOFORCE] VIEW <view_name> [(alias [, alias]…)] © SQL Star International Ltd. 322
  • 326. AS subquery [WITH CHECK OPTION [CONSTRAINT <constraint_name>]] [WITH READ ONLY]; Where, OR REPLACE changes the definition of a view without dropping or re-creating it. FORCE forces the creation of a view even without the existence of a base table. NOFORCE this is the default option. It creates a view only if the base table exists. view_name is the name given to the view that is created. alias specifies the names for the expressions which will hold the values of the columns selected by the subquery. subquery is the SELECT statement which retrieves the columns that the view must have. WITH CHECK OPTION is a type of CHECK constraint, which specifies that only those rows that are selected by the view can be inserted, updated or deleted. CONSTRAINT constraint_name assigns a name to the CHECK OPTION constraint. WITH READ ONLY prevents any DML operations from being performed on the view. Points to remember while creating views:  The subquery can contain complex SELECT statements, that is, SELECT statements, which include joins and group functions.  The subquery cannot contain an ORDER BY clause. Specify the ORDER BY clause while retrieving data from the view. Creating Simple Views Simple views are created by embedding a subquery that retrieves data only from a single table, within the CREATE VIEW statement. For example, in order to prevent the librarian of the ‗Randolph NJ Library‘ from accessing or modifying the book details of other branches, the library database developer creates a view that shows details of only those books that are stored in the ‗Randolph NJ Library‘. In order to create this view the developer would have to execute the following code: © SQL Star International Ltd. 323
  • 327. CREATE VIEW vwRandolphBook As SELECT cBookID, cBookName, cAuthorName, cCategoryID, cPublisherID, dPublishedYr, nNoOfCopies FROM Book WHERE cBranchID = '04RANNJ' ; View created. On executing the code, vwRandolpBook view gets created containing book details of only the Randolph branch, which is identified by its ID ‗04RANNJ‘. The structure of the vwRandolpBook view can be displayed by issuing the iSQL*Plus DESCRIBE command. DESCRIBE vwRandolpBook Enforcing Constraints on Views The base tables have constraints defined on them that limit the kind of data that can be entered or modified. The views that are based on them too have the same restrictions. In addition, special constraints can also be enforced on views. This is made possible by using:  The WITH CHECK option  The WITH READ ONLY option The WITH CHECK OPTION This option protects data integrity and performs data validation checks by ensuring that the data being changed is the data the view can select. It sees to it that any inserts or updates being performed through the view do not create rows that the view cannot select. For example, due to the frequent enquiries made by its members regarding the books stored © SQL Star International Ltd. 324
  • 328. in the ‗Princeton‘ branch (which has been assigned an ID 05PRINJ), the library database developer decides to create a view that will contain details about all the books the ‗Princeton‘ branch stores. But, the developer must ensure that the librarian accessing the view does not make any changes to the data stored. To ensure this the following code must be executed: CREATE OR REPLACE VIEW vwPrincetonBks AS SELECT * FROM Book WHERE cBranchID=‗05PRINJ‘ WITH CHECK OPTION CONSTRAINT PrincetonBkCK; View created. The code creates a vwPrincetonBks view with the WITH CHECK OPTION clause. By specifying the WITH CHECK OPTION constraint, any attempt made by the librarian to manipulate the branch ID for any row in the view will fail. For example, if the branch ID of the book were changed to ‗01ADLNJ‘, the view would no longer be able to select that book and therefore the following DML operation performed fails: UPDATE vwPrincetonBks SET cBranchID=‗01ADLNJ‘ WHERE cBookID=‗FIC050003232‘; Displays an error: Error at line 1: ORA-01402: view WITH CHECK OPTION where-clause violation The WITH READ ONLY option Using the WITH CHECK OPTION ensures that the DML operations being performed are within the scope of the view, that is, DMLs are performed on rows that the view can select. But, how to ensure that no DML operations are performed? This can be ensured by using the WITH READ ONLY option. This option prevents any DML operation from being performed on the view. If any attempt is made to perform DMLs on any row in the view, the Oracle server will generate an error. For instance, if the DBA creates a view for the clerk ‗Brad Riley‘, he needs to ensure that ‗Brad Riley‘ does not write into the view. The following code will help: CREATE OR REPLACE VIEW vwHamiltonBks AS SELECT * FROM Book WHERE cAuthorName=‗Shakespear‘ AND cBranchID=‗03HAMNJ‘ WITH READ ONLY; © SQL Star International Ltd. 325
  • 329. View created. The view vwHamiltonBks is created by adding the WITH READ ONLY option, which prevents any DML operations from being performed on it. If ‗Brad Riley‘ attempts to delete any row from the view, he encounters the following error: DELETE FROM vwHamiltonBks WHERE cBookName=‗Othello‘; Error at line 1: ORA-01752: Cannot delete from view without exactly one key-preserved table Similarly, if he attempts to add or modify a row, the Oracle server would generate the following error: UPDATE vwHamiltonBks SET nNoOfCopies=6 WHERE cBookName=‗Othello‘; ERROR at line 2: ORA-01733: virtual column not allowed here Rules for Performing DML operations The user of a view can insert, update or delete data on the underlying table if the creator of the view allows him/her to do so. However, there are a few restrictions that apply when the user of a simple view attempts to perform any DML operations:  The user cannot insert, update or delete data on the underlying table, if the view itself cannot select that data. This happens if the WITH CHECK OPTION is used.  The user cannot insert, update or delete data on the underlying table, if the subquery that defines the simple view contains:   GROUP BY or ORDER BY clause  Any single-row or group function  The DISTINCT keyword  Columns defined by expressions such as nNoOfCopies *2  The user cannot perform any DMLs if any references to virtual or pseudo columns such as ROWID, CURRVAL, NEXTVAL and ROWNUM are made by the © SQL Star International Ltd. 326
  • 330. subquery. Pseudo-column is not an actual column of any table but returns an Oracle generated value when selected.  The user cannot perform any DMLs if the WITH READ ONLY option is used in the subquery.  The user cannot add data into the underlying table if it‘s NOT NULL column is not selected by the subquery. For example, the librarian cannot insert data into the Book table if the vwRandolpBook view does not select the cBookID column. This is because cBookID is a primary key column implying that it cannot contain null values. (Remember that you are attempting to insert values directly into the base table through the view.) Creating Complex Views Complex views are created by embedding a subquery that retrieves data from more than one table, in the CREATE VIEW statement. In addition to joins, the subqueries can possibly contain:  Single-row as well as group functions  References to pseudo columns  GROUP BY clauses Complex views are created for concealing complexities involved in retrieving data such as the performance of joins or using group functions to obtain the result set. For example, members may request the librarian to provide a list of all the books stored in the ‗Randolph NJ Library‘ branch complete with their category names. To do so the librarian would have to cross-check both the Book as well as the Category tables. This proves to be quite taxing, especially if queries of the similar kind increase. To overcome this, the developer creates a view by joining the two tables. The librarian then needs to only query this view without even knowing that it is based on two tables. Executing the following code would create the view: CREATE OR REPLACE VIEW vwRandolphBooks AS SELECT B.cCategoryID, C.cCategoryName, B.cBookID, B.cBookName, B.cAuthorName,B.dPublishedYr,B.nNoOfCopies FROM Book B,Category C WHERE B.cCategoryID=C.cCategoryID AND B.cBranchID=‘04RANNJ‘; View created. On the execution of the code, a complex view gets created wherein the subquery contains a join condition. © SQL Star International Ltd. 327
  • 331. SELECT cCategoryName,cBookName FROM vwRandolphBooks; CCATEGORYNAME CBOOKNAME ------------- --------------- Math Aha! Gotcha: Paradoxes to Puzzle and Delight Children Amelia Jane is Naughty Again ..... .............. ..... .............. 38 rows selected. But, if the library clerk wants to know the total number of copies of books of each category that the library stores, then the above view would not serve the purpose. To do so, the developer would have to create a view by executing the following code: CREATE OR REPLACE VIEW vwBookCopies (Category,TotalCopies) AS SELECT C.cCategoryName,SUM(nNoOfCopies) FROM Book B,Category C WHERE B.cCategoryID=C.cCategoryID GROUP BY C.cCategoryName; View created. On executing the code, a complex view vwBookCopies gets created that contains a group function. The clerk can display the contents of the view by executing a SELECT statement. SELECT * FROM vwBookCopies; The statement retrieves the following result set: CATEGORY TOTALCOPIES ---------- --------- Archaelogy 25 Children 136 © SQL Star International Ltd. 328
  • 332. Classic 92 Computers 36 Fiction 55 History 52 Humor 74 Math 56 Mechanical 31 Mystery 83 Non Fiction 58 Psychology 40 Romance 59 Science Fiction 45 14 rows selected. Complex views do not allow data to be added, changed or deleted on the underlying table because of the join that is performed. Therefore, it is not necessary to specify the WITH READ ONLY option as complex views are already considered to be read only. N.B.:- This can be resolved by creating INSTEAD OF triggers, which will be dealt in a later chapter. Constraints on Views One of the Oracle9i constraint enhancements has been with regards to the ability to create primary and foreign keys on views. Now, you can specify constraints on view columns. However, view constraints are declarative only. That is, they are not enforced by the Oracle database. View constraints are subject to the following restrictions: © SQL Star International Ltd. 329
  • 333.  Only unique, primary key and foreign key constraints can be specified on views.  You cannot specify clauses like DEFERRED or DEFERRABLE because view constraints are not enforced.  View constraints can be specified only in the DISABLE NOVALIDATE mode.   Clauses such as USING INDEX, EXCEPTIONS INTO, or ON DELETE clause cannot be specified in view constraints. Creating Inline Views In addition to creating simple and complex views, you can also create Inline Views. Inline views are named subqueries (a subquery with an alias) written in the FROM clause. The named subquery defines the source of data for the main SELECT statement. For example, the library clerk would be required to produce a list of books whose number of copies stored is less than the maximum number of copies of books stored in their respective branches. To produce the desired result, the developer would have to first retrieve the maximum number of copies of books stored in each branch. SELECT cBranchID,MAX(nNoOfCopies) MaxCopies FROM Book GROUP BY cBranchID; CBRANCH MAXCOPIES ------ -------- 01ADLNJ 9 02CHSNJ 9 03HAMNJ 9 04RANNJ 8 05PRINJ 9 The developer would have to then cross check the query output with the Book table in order to find out those books whose number of copies stored is less than the maximum number of copies of books stored in their branches. © SQL Star International Ltd. 330
  • 334. The developer could instead write the above SELECT statement as a subquery in the FROM clause of a main query as shown next: SELECT B.cBookName Book,B.nNoOfCopies Noofcopies,B.cBranchID BranchID,C.MaxCopies ―Max Copies‖ FROM Book B, (SELECT cBranchID,MAX (nNoOfCopies) MaxCopies FROM Book GROUP BY cBranchID) C WHERE B.cBranchID = C.cBranchID AND B.nNoOfCopies < C.MaxCopies; The query displays the following result set: BOOK NOOFCOPIES BRANCHI Max Copies --------- -------- ------ -------- Archaeology as Cultural History 6 01ADLNJ 9 Fractals Everywhere 2 01ADLNJ 9 ............... .. ... . . 173 rows selected. In the code, the SELECT statement inside the parentheses is used as one of the ―tables‖ in the query and is given an alias, C. It is treated just as if it were a view. It is this named subquery that is known as an inline view. Writing the following join condition joins the Book table and the inline view: …WHERE B.cBranchID = C.cBranchID… This join condition produces the same output that you would get by cross checking the result of the subquery manually with the Book table. Oracle7 and Oracle8 did not allow the use of the ORDER BY clause within subqueries. But since Oracle8i you can use the ORDER BY clause with inline views. The following code will illustrate the use of the ORDER BY clause: © SQL Star International Ltd. 331
  • 335. SELECT M.Name FROM (SELECT cFirstName||cLastName Name FROM Member ORDER BY Name) M; The query displays the following result: NAME ----------------- Andre Cobb Austin Dinsmore Bridgette Wells Celena Stevenson Cresinda Finch Darla Green Derian Bates Eveangela Gammons Ferdinand Swander ---------- ------- 21 rows selected. The Inline view retrieves a sorted list of member‘s names by concatenating their first names with last names. This inline view defines the data source for the SELECT statement. The execution of the code does not result in any error despite the use of the ORDER BY clause. The importance of using the ORDER BY clause in inline views can be seen when you need to retrieve the n largest or smallest values of a column. Top-N Analysis Top-N analysis or top-n queries are used to retrieve the n largest or smallest values of a column. For example, there may be queries to retrieve the ten most recently registered members in the library or to retrieve the four most senior members of the library. To retrieve the desired results, you will have to use top-n queries. The syntax for creating a top-n query is: © SQL Star International Ltd. 332
  • 336. SELECT column_list, ROWNUM FROM (SELECT column_list FROM <table_name> ORDER BY Top-N_column) WHERE ROWNUM <= N; Where the top-n query consists of: • A subquery or an inline view which includes the ORDER BY clause to ensure that the results are retrieved in the desired order. Specifying the ORDER BY clause retrieves the top n smallest values of a column. In order to retrieve the top n largest values use DESC keyword along with the ORDER BY clause. • An outer query that limits the number of rows that is to be retrieved. It comprises of:   The ROWNUM pseudocolumn, which assigns successive values to each of the rows returned by the subquery, and   The WHERE clause, which specifies the number of rows that are to be returned. The WHERE clause must use a < or <= operator. The outer query limits the number of rows by WHERE ROWNUM <= N. Using Top-N Queries If the developer has to find out the four most recently registered members of the library, he would have to issue the following SELECT statement: SELECT ROWNUM ―NEW MEMBERS‖,M.Name, M.MembershipDt FROM (SELECT cFirstName||cLastName Name, dMembershipDt MembershipDt FROM Member ORDER BY dMembershipDt DESC) M WHERE ROWNUM <= 4; In the code, the inline view M returns the names and the membership dates from the Member table, which are sorted in the descending order of the membership dates. The outer query selects the pseudocolumn ROWNUM, which assigns sequential values to the rows that are returned by the inline view. The rows returned are limited by the WHERE ROWNUM <= 4 clause, which ensures that only four rows from the resultant rows are displayed. NEW MEMBERS NAME MEMBERSHIP ------------- ----------------- --------- © SQL Star International Ltd. 333
  • 337. 1 Norbert Cambell 03-MAR-01 2 Johna Butler 19-SEP-00 3 Eveangela Gammons 10-APR-00 4 Ferdinand Swander 03-MAR-00 Using Views The users using views find that accessing data from the views is similar to accessing data from a table. They can even modify or remove views just as they would do to a table. Data Access from Views Before you access data from a view, you need to confirm its creation by querying the USER_VIEWS data dictionary table. In order to display the contents of USER_VIEWS issue the DESCRIBE command. DESCRIBE USER_VIEWS Name Null? Type --------- --------- --------- VIEW_NAME NOT NULL VARCHAR2(30) TEXT_LENGTH NUMBER TEXT LONG TYPE_TEXT_LENGTH NUMBER TYPE_TEXT VARCHAR2(4000) OID_TEXT_LENGTH NUMBER OID_TEXT VARCHAR2(4000) VIEW_TYPE_OWNER VARCHAR2(30) VIEW_TYPE VARCHAR2(30) © SQL Star International Ltd. 334
  • 338. USER_VIEWS data dictionary view displays the name of the view as well as the view definition. The view definition is stored in the dictionary table as SELECT statements. The text of the SELECT statements is stored in a LONG column. For example, the developer of vwRandolpBook view could confirm its creation by viewing USER_VIEWS. SELECT * FROM USER_VIEWS; When a user attempts to access data using a view, the Oracle server retrieves the view definition from USER_VIEWS and converts it into a similar query on the underlying table, thereby retrieving data from the base table. For example, when the librarian attempts to retrieve data using vwRandolpBook view, he would issue the following SELECT statement: SELECT * FROM vwRandolpBook; On encountering the above statement, the Oracle server retrieves vwRandolpBooks views definition from USER_VIEWS data dictionary. The view definition on being retrieved would be: SELECT TEXT FROM USER_VIEWS WHERE VIEW_NAME=‘VWRANDOLPHBOOK‘; Displays: TEXT -------------------------------- SELECT cBookID,cBookName,cAuthorName, cCategoryID,cPublisherID,dPublishedYr,nNoO The Oracle server then converts the view query into a similar query on the underlying base table and retrieves data from the base table. Modifying Views There are situations when the developers of views are required to make some modifications to the views. The statement used to modify a view is the CREATE OR REPLACE VIEW statement. On issuing a CREATE OR REPLACE VIEW statement, the Oracle server overwrites the old © SQL Star International Ltd. 335
  • 339. definition of the view with the new one by overlooking the error that arises on encountering an already existing view with the same name. The following code illustrates the use of the CREATE OR REPLACE VIEW: For example, the user of the vwRandolpBook view may suggest the developer that more meaningful names be assigned to the columns as they currently have the same names as the columns of the underlying Book table. To do so the developer would have to modify the view by specifying column aliases. CREATE OR REPLACE VIEW vwRandolpBook AS SELECT cBookID BookId,cBookName BookName,cAuthorName Author, cCategoryID CatgID, cPublisherID PublisherID, dPublishedYr PublishedYr, nNoOfCopies Copies FROM Book WHERE cBranchID=‘04RANNJ‘; View created. In the code, the OR REPLACE option replaces the old version of the vwRandolpBook view with the new one. The execution of the above code controls the column names by specifying aliases in the subquery. The column aliases can also be specified in the CREATE VIEW clause. But they must be listed in the same order as the columns that are selected by the subquery. The following code will illustrate how to specify column aliases in the CREATE VIEW clause: CREATE OR REPLACE VIEW vwRandolpBooK (BookID,BookName,Author,CatgID,PublisherID,PublishedYr,Copies) AS SELECT cBookID,cBookName,cAuthorName,cCategoryID, cPublisherID,dPublishedYr,nNoOfCopies FROM Book WHERE cBranchID=‘04RANNJ‘; View created. Just as there is the ALTER TABLE statement to modify the table structure, similarly there is an ALTER VIEW statement available in the Oracle SQL language. The syntax is: ALTER VIEW view_name; But instead of being used to modify the view structure, it is used to recompile a view that becomes invalidated either due to: © SQL Star International Ltd. 336
  • 340.  Change made to the definition of the underlying table  Deletion of the underlying table To rectify the invalidated view you must either recreate the underlying table and issue the ALTER VIEW statement or modify the view by using the CREATE OR REPLACE VIEW statement. Removing Views There may arise situations that would require the developer of a view to remove it from the database. The statement used to remove a view is the DROP VIEW statement. Removing a view does not affect the table on which it was based. Only the view definition is removed from the database. The syntax for dropping a view is: DROP VIEW <view_name>; Where, view_name is the name of the view that is to be dropped For example, the developer creates a view to display the addresses of all the library members, based on the requirement made by the librarian for the purpose of sending mails to them. The developer executes the following code to create the view: CREATE OR REPLACE VIEW vwMemberAddress AS SELECT cFirstName,cLastName,vAddress, cArea,cZipcode FROM Member; View created. After querying the vwMemberAddress view, the librarian would be able to retrieve the addresses of members and accordingly send mails to them. SELECT * FROM vwMemberAddress; The query displays the following result: CFIRSTNAME CLASTNAME VADDRESS CAREA CZIPCODE © SQL Star International Ltd. 337
  • 341. -------- -------- ----------- -------- ------- Austin Dinsmore 41B, Cliftwood Avenue, Allenbury NJ01956 Fourth Cross Rd Bridgette Wells 65A, Maple Breeze Apts, Ridgeland NJ04352 Redford Township Celena Stevenson 19-22A, Free Gallop Villa, Roxbury NJ90231 Greenwich Hallway Rd Ferdinand Swander 909D, Sunrise Marble Apts, Stanhope NJ12543 Springwood Lane ---------------------- 21 rows selected. After sending mails, the librarian would no longer need to query the view as his purpose has been met. Therefore, the developer (on being told by the librarian) would decide to remove the view from the database. The developer of the vwMemberAddress view would execute the DROP VIEW statement to drop the view. DROP VIEW vwMemberAddress; View dropped. Execution of this code removes the vwMemberAddress view from the database. © SQL Star International Ltd. 338
  • 342. Summary In this chapter, you have learnt that:  Views are virtual tables based on the underlying database tables. They can be visualized as a window to a base table.  Views provide restrictive access to the base table, hide the complexity of joining multiple tables and can provide specific information for different users.  Views based on single table are known as simple views. DML operations can be perfomed on these views directly.  Views based on Multiple tables are known as complex views. DML operations can be done on these views through triggers only.  Views are created using CREATE VIEW statement and modified using CREATE OR REPLACE VIEW statement.  Inline views are named subqueries (a subquery with an alias) written in the FROM clause. The named subquery defines the source of data for the main SELECT statement. TOP-N analysis can be performed using Inline view.  Constraints can be applied on views using WITH CHECK options and READ ONLY clauses.  Information regarding Views can be fetched using USER_VIEWS data dictionary view. © SQL Star International Ltd. 339
  • 343. Lab Exercise 1. Create a view vwDept50EmpDetails to display the following of employees belonging to department number 50:  IDs  First name and last names concatenated together and named as Employees  Job IDs  Salary Retrieve the contents of the view. The view should display the contents as shown below. 2. Create a view vwDeptSalaryDetails to display the maximum, minimum, and average salaries of each department. The view should display the results as follows: © SQL Star International Ltd. 340
  • 344. 3. Make the following modifications to vwDept50EmpDetails:  Include the department number in the view  Ensure that any attempt to reassign an employee to any other department through the view fails After making the modifications, try and update the department number of employee ID to 120. What error message do you get? 4. Create a view vwEmpDetails, which should display the following:  Employee first name and last name concatenated and given an alias Name  Department name  Job title  City name  Country name  Region name  Salary Ensure that no DML operations can be performed on the view. The view should display the result as shown below. © SQL Star International Ltd. 341
  • 345. 5 Retrieve the view name and view text of vwDept50EmpDetails, vwDeptSalaryDetails and vwEmpDetails views from USER_VIEWS data dictionary view. [Hint: For better readability, use the iSQL*Plus SET LONG n, where n is the number of characters of the LONG column you would want to see] 6. Create an inline view to display the last name, department number, salary and average salary for all those employees who earn a salary less than the average salary in their respective departments. On querying the view, the following result should be displayed: 7. Write a query to display the last names and salaries of the top 10 salary earners. The query should display the following result: © SQL Star International Ltd. 342
  • 346. Chapter 15 Other Database Objects Indexes Types of Indexes B-Tree Index Bitmap Index Working With Indexes Index Organized Tables Sequences Synonyms © SQL Star International Ltd. 343
  • 347. Objectives At the end of this chapter, you will be able to: State the need for Indexes Use Indexes Define the role of Sequences Use Sequences Use Synonyms Indexes When you request for a particular row of data, the server does a full table search and when the requested row is found, it is retrieved and displayed. The process of full table scan takes a lot of time and also uses up a lot of the system resources. To quicken the process, you can create an index. An index is a database object with which you can increase the speed of data retrieval. Following are the uses of indexes:  Indexes ensure that all data in a column with an index is unique.  Indexes ensure faster retrieval of data. Creation of Indexes Indexes are created to enforce integrity constraints for uniqueness. Indexes are created either:  Automatically  Manually Automatic Creation Automatic indexes are called so, because the Oracle server creates them. These indexes are created when a table with a column having the primary key or the unique key constraint, has been created. When the constraint and its supporting index is created and the column values are put into it, the index takes its name after the constraint. In case you do not name the constraint when creating the table, the system gives the index a name like SYS_28349240. Automatic indexes are created basically to enforce the uniqueness check. The difference between an index created with the primary key and that with a unique constraint index is that the former does not allow NULL values and the latter does. © SQL Star International Ltd. 344
  • 348. There could be requirements in a database for indexes other than the ones that are automatically created. These need to be created manually. Manual Creation Manual indexes are created using the CREATE INDEX statement. They are not different from the indexes that are created automatically. The only way you can differentiate an automatically created index from a manually created one is from its name. You would follow some naming convention of your own to name the index you create. For example, an index of a primary key in the Member table of the library database could be called idxMemberPK. The Oracle server follows its own conventions for naming indexes. The syntax for creating an index is as follows: [This is not the complete syntax. It is dealt in depth later in this topic.] CREATE INDEX <index_name> ON <table_name> (column[, column]…); Where, index_name is the name you assign to the index you are creating. table_name is the name of the table whose column you are attempting to index. column is the name of the column in the table you are trying to index. You can create non-unique indexes to speed up the accessing of rows. For instance, the library desk officer has to frequently query the Book table to retrieve books based on their author names. To speed up the access time, the database developer could create an index on the author name column using CREATE INDEX statement as follows: CREATE INDEX idxAuthorName ON Book (cAuthorName); On successful creation of the index, you get the following message: Index created. Types of Indexes The types of indexes available are:  B-tree index  Bit-map index  Non Unique Index  Compressed Index  Function-based index © SQL Star International Ltd. 345
  • 349. B-Tree Index B-tree is the traditional index of the Oracle database and is based on a complex algorithm of sorting. Data in a B-tree is stored in a top to bottom manner resembling an inverted tree. This kind of data storage is based on the binary search tree concept. The highest level of the data store is called the root-node and is depicted on top of the inverted tree. The data is in a sort of a list and is arranged in a layered and branching manner. When the values are stored in this manner the data does not have to be searched in a sequential manner, which is time consuming. It is suggested that data should be stored in this manner when the column has many distinct values or when the column is unique. The B-tree consists of branch nodes, leaf nodes and data blocks. The algorithm of a B-tree is as follows: 1. Data is stored in the form of a list with the midpoint of the list as the root- node. Each section‘s midpoint is in turn made the next level and so on. 2. The data to be searched is compared with the values at the midpoint. If the value is greater, then the values below the midpoint are eliminated. If the search value is lower than the midpoint value, the values above the midpoint are eliminated. 3. This process is performed with every successive section and its midpoint, till the value is found. © SQL Star International Ltd. 346
  • 350. Nodes store certain important information referred to as ROWID. This stores information about the row location of the value on the disk. These are pointers to the data values. Data is stored in an order and the NULL values if any are not indexed. Multiple data blocks are read at a time enabling faster scan of data. Rows of data are found by traversing the branches of the tree and scanning the leaf blocks. If the search required more columns, then the data block is accessed. Let us take an example to understand B-Tree Index better. From the above tree structure if we want to find the value of 45, we start from the top of the tree and move towards the right. We would read the block and find that we should go to the block in the range ‗less than 50 to 40‘. This block will be the leaf block and point to the rows containing the number 45. Note that the blocks in the leaf nodes are doubly linked. This would help us in solving range scans because all we need to do is to identify where to ‗start‘ in the leaf node and once it‘s found doing an ordered scan of values is very easy. © SQL Star International Ltd. 347
  • 351. For example, To solve the query, SELECT * from <table name> where x between 20 and 30; Oracle will simply find the index block that contains 20 and from there the scanning goes horizontally till 30. Here the advantage is that it does not have to navigate through the entire tree structure again. Bitmap A bitmap index is structured like a matrix where the data value in a table column is shown in columns along one axis of the matrix. The other axis contains the ROWIDs. Every value is represented in one column; hence if a column in a table has too many distinct values the index will become larger. Therefore, this kind of index is best applied to a table where there are as few distinct values (also referred as low cardinality columns) as possible. Indexes are also classified as unique and non-unique depending on the data that they store. Consider the Member table in the Library example explained in this book. Two columns are ideal candidates for bitmap index namely cMaritalstatus (Only Y/N) and cGrade (A/B/C/D). MEMBERID CGRADE CMARITALSTATUS -------- ------- ---------------- © SQL Star International Ltd. 348
  • 352. CDB028504 C N BAD109001 B N CBW109702 C Y ACS099903 A N DFS030005 D Y BKF079702 B N CNC030103 C N BLB089904 B N ........... ........ ......... etc Once the bitmap index is created on CMARITALSTATUS, Oracle will store something like the following table. Cmaritalstatus_bitmap_ind Considering bitmap index being created for Cgrade the structure would be Cgrade_bitmap_ind © SQL Star International Ltd. 349
  • 353. In the first row marital status is ‗N‘ so the bit ‗N‘ is ‗1‘, in the third row the marital status is ‗Y‘ so the bit is ‗1‘ and the value for ‗N‘ is ‗0‘ so the bit is ‗0‘ and so on. In the Bitmap index of cGrade, first row is ‗C‘ so the bit Corresponding is ‗1‘. Similarly, in the 5th row, the value for grade is D; hence, it is equivalent bit in column D is ‗1‘. Consider a query, SELECT count(*) FROM Member WHERE cmarital status =‘ N‘ AND Cgrade IN(‗C‘,‘B‘); The above query involves the bitmap of ‗N‘, ‗C‘ and ‗B‘. While processing, the bitmap ‗N‘ ‗C‘ and ‗B‘ will be taken as ‘N’ ‘C’ ‘B’ 0 1 1 0 1 1 0 1 0 1 AN 0 OR 0 0 0 0 1 D 0 1 1 1 0 1 0 1 The result of ‗OR‘ operator combined with ‗AND‘ is calculated to fetch the final resultant. © SQL Star International Ltd. 350
  • 354. From the Bitmap result there are 5 records satisfying the condition, because there are 5 ones (1) in the result set. As discussed earlier, the server creates unique indexes automatically, when a column of a table is set with the unique or primary key constraint. The structure of a unique index is a B-tree. Non-unique The non-unique index is manually created on a column, which is most frequently used for queries. The data in the column may contain duplicate values. This could be an index on a foreign key column of a table. Compressed Index © SQL Star International Ltd. 351
  • 355. This type of index saves the disk storage by storing the repeated portion of the column value (Key), just once, depending on the degree of compression. There are a lot of real applications that can use this type of index effectively. Consider an application which maintains a table for storing object details created for an application like owner, object type and object name. Whenever new objects are created it gets a new entry in the table. When application wants to retrieve that information it can have a compressed index, which saves lot of space in the disk. Considering the three columns mentioned above the data would be something like this: SCOTT.TABLE.MYTAB SCOTT.TABLE.EMP SCOTT.TABLE.DEPT SCOTT.PROCEDURE.P1 PROCEDURE.P2 .... ... An uncompressed index for the above data would be like the sample data above, which is a concatenated index on all the three columns. For a compressed index with a degree of compression ‗1‘ it will be CREATE INDEX myindex ON <tablename>(OWNER,OBJECTNAME,OBJTYPE) COMPRESS 1; In this case the storage would be, The above Index would definitly occupy less space ,since the key (username) is stored only once. © SQL Star International Ltd. 352
  • 356. Function-Based Index Another kind of index is a function-based index. This index is created based on the expression used in the SELECT statement or other DDL statements. This query helps you to use the index to search for data rather than do an entire table scan. To ensure this, you need to specify the WHERE clause with the condition that the column of the values of the expression does not contain a NULL. If you do not specify the clause, the server may scan the entire table. For instance, the following query could have been implemented with a complete table scan if the WHERE clause was not specified: SELECT * FROM Transaction WHERE nFine IS NOT NULL ORDER BY nFine; Prior to Oracle9i, all the columns used in the function-based index had to be declared NOT NULL. But from the 9i release, even if the expression contains a NULL value, the built-in operators recognize them as NOT NULL and give a result that is NOT NULL. Therefore, the function-based index will contain NOT NULL values and the index-only scan can be performed on it. © SQL Star International Ltd. 353
  • 357. Working with Indexes Using an index involves creating it and following some guidelines to do so. There can be some negative consequences if a table has too many indexes. You should be able to manipulate the index and perform tasks related to maintaining all the indexes in a database. Creating an Index The process of creating an index comes into picture when you need to create it manually. Unique and primary indexes are automatically created by the system when the respective constraints are set on table columns. These indexes can also be manually created by using the CREATE INDEX statement. You need to specify the type of index to be created with the CREATE INDEX statement. For instance, the syntax to create a unique index is as follows: CREATE UNIQUE INDEX <index name> ON <table name> (column_name); Where, CREATE INDEX is the key word to create the index UNIQUE is the keyword that specifies that a unique index is to be created <index name> is a name for the index <table name> is the table on which the index is to be created. column_name is the name of the column on which the index has to be created For example, for faster retrieval of data from the NonMember table, you can create a unique index on the nSerialNo column as follows: CREATE UNIQUE INDEX idxNonMemSer ON NonMember(nSerialNo); © SQL Star International Ltd. 354
  • 358. Index created. You can also create an index:  On more than one column thus creating a composite index  Of bitmap type by using the BITMAP keyword instead of UNIQUE However, creating an index is not very easy. You need to think about query performance, database performance and size and requirement of the indexes to be created. An index is needed to be created according to the requirements of a table. You need to decide when to create a B-tree index and when to create a bitmap index. If you create many indexes on a table it does not imply that the data retrieval speed increases. On the contrary, any manipulations to the table data needs to be reflected on the indexes and this could be a time taking process. Some points to help you decide when it is best to create indexes are given below:  A particular column (or columns) is frequently used in the WHERE clause of a SELECT statement or in a JOIN condition.  The column holds a large range of values or a large number of NULLS. The table is of a large size and the result set of a query is less than 2-4 % of the rows in the table. There are some cases, like the following, where creating an index may not prove to be useful:  If the table in question is small in size  If the columns of a table are not frequently used in a query  If the result set of a query is expected to be about 2-4 % of the rows in the table  If the table requires frequent updates. In this case, every time the table is updated all the indexes on the table need to be updated too. Altering an Index You cannot make many changes to an existing index directly. If you want to change the structure of an index, you need to first remove the index completely and recreate it with the new specifications. View Index Structure You can check if there are any indexes that have been created. Whether created manually or automatically, all indexes are stored in the database with their structure definition. You can confirm the existence of the indexes in a database by using the USER_IND_COLUMNS. The information stored in this data dictionary is the name of the index, the column name on which the index is created and the table name. © SQL Star International Ltd. 355
  • 359. The ALL_INDEXES data dictionary view contains information about the storage of indexes. The names of the tables of the indexes are also stored. The USER_INDEXES data dictionary view displays the names of indexes and the type of index it is (that is, its uniqueness). Using the data dictionary views, confirm the creation of your indexes. SELECT ic.Index_Name, ic.Column_Name, ic.Column_Position col_pos, ui.Uniqueness FROM USER_INDEXES ui, User_Ind_Columns ic WHERE ic.Index_Name = ui.Index_Name AND ui.Table_Name IN (‗NonMember‘,‘Book‘); The above SELECT statement displays the following result: INDEX_NAME COLUMN_NAME COL_POS UNIQUENES ---------- ----------- -------- ---------- IDXAUTHORNAME CAUTHORNAME 1 NONUNIQUE BOOKBOOKIDPK CBOOKID 1 UNIQUE IDXNMEMSER NSERIALNO 1 UNIQUE Removing Indexes Once indexes are created and if the users no longer require them, they can be deleted. You can remove an index by using the DROP INDEX command. When an index is dropped, it is removed from the data dictionaries and indexed searches are no longer performed on the database. If the index was based on a constraint like UNIQUE, then it will not enforce the constraint. The syntax for removing the index is: DROP INDEX <index_name> The unique index that you created on the NonMember table can be deleted as follows: DROP INDEX idxNMemSer; Index dropped. You can verify if the index is deleted by viewing the USER_INDEXES data dictionary view. SELECT index_name © SQL Star International Ltd. 356
  • 360. FROM USER_INDEXES WHERE table_name=‘NONMEMBER‘; The above statement displays: no rows selected. Index Organized Tables Each row in a table has a physical location with a unique ROWID assigned to it. As long as the row exists, its physical ROWID does not change. When you create an index on a table, the index contains both the column data and the ROWID, and the index is stored in a memory location separate from the table. As a result, the column values are repeated, thereby causing redundancy. Secondly, each query that uses the index increases the I/O operation of following a ROWID back to table data. Therefore, in Oracle8, concept of Index Organized Tables (IOTs) was introduced. Index Organized Tables are tables, where the index is created and stored within the table. Compared to an ordinary table, an IOT has its own way of structuring, storing and indexing data. A row in an IOT does not have a permanent physical address and can move across data blocks when new rows are inserted. An IOT is implicitly indexed on the primary key. The table data is sorted in order of the B-tree index, which is created on the primary key of the table. The IOTs provide fast access to table data for queries involving exact match or range search based on a primary key. It also reduces storage requirements as the indexed column values are not duplicated in both the table and the index and no additional storage is needed for ROWIDs. Index Organized Tables are ideal for the following kinds of applications:  Online Transaction Processing (OLTP)  Internet (search engines and portals)  E-Commerce © SQL Star International Ltd. 357
  • 361.  Data Warehousing  Time-series applications The syntax to create an Index Organized Table includes an additional ORGANIZATION INDEX clause in the CREATE TABLE command. The following command creates an IOT StudentDetails, with studentID as primary key column: CREATE TABLE StudentDetails (studentID CHAR(2), studentName VARCHAR(40), courseID CHAR(2), marksTot NUMBER(4), CONSTRAINT student_c_pk PRIMARY KEY (studentID)) ORGANIZATION INDEX; Table created. The ORGANIZATION INDEX clause indicates that the table should be an IOT. Do queries fail to use index? Yes, in some cases queries fail to use an index. Let us see some cases here. Case 1: If the indexed column is mentioned along with a function, the index usage will be nullified. For example: SELECT * FROM Member WHERE UPPER(cFirstName)=‘VELADA‘; This results in Full Table Scan (FTS). This is because, we have indexed on cFirstName column not on UPPER (cFirstName). N.B : We can index the function if we choose to do it using Function Based Index. Case 2: The indexed column, cPhone has numeric data. But since no calculations are done on it, it is defined as a character column. When a query is given with a following syntax, SELECT * FROM Member WHERE cPhone=9600102033; Note that the phone number is not given in single quotes, so while processing, Oracle will process it as shown below. SELECT * FROM Member WHERE TO_NUMBER(cPhone)=9600102033; Hence, it will not use the index. © SQL Star International Ltd. 358
  • 362. How do we check the usage of the Index? In order to check the usage of the index for a given query, developers can use a statement as a tool known as EXPLAIN PLAN to determine the execution path of an SQL statement. The Execution plan is stored in a TABLE called PLAN_TABLE whose structure is described below. SQL > DESC PLAN_TABLE The structure of the table will be shown as: Name Null? Type --------------------- -------- --------------- STATEMENT_ID VARCHAR2(30) PLAN_ID NUMBER TIMESTAMP DATE REMARKS VARCHAR2(4000) OPERATION VARCHAR2(30) OPTIONS VARCHAR2(255) OBJECT_NODE VARCHAR2(128) OBJECT_OWNER VARCHAR2(30) OBJECT_NAME VARCHAR2(30) OBJECT_ALIAS VARCHAR2(65) OBJECT_INSTANCE NUMBER(38) OBJECT_TYPE VARCHAR2(30) OPTIMIZER VARCHAR2(255) SEARCH_COLUMNS NUMBER ID NUMBER(38) PARENT_ID NUMBER(38) .... ..... .... ..... Syntax for using EXPLAIN PLAN: EXPLAIN PLAN FOR <statement>; Case 1. Consider querying from the Member table with out any index. SQL> EXPLAIN PLAN FOR SELECT * FROM Member WHERE cArea=‘Allenbury‘; Displays: Explained. In order to get the formatted output of the execution plan, run the following script. SQL> @<Oracle_home>RDBMSadminutlxpls PLAN_TABLE_OUTPUT © SQL Star International Ltd. 359
  • 363. ------------------- Plan hash value: 3441279308 ---------------------------------------- | Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time | ------------------------------------------------------------------ | 0 | SELECT STATEMENT | | 2 | 24 | 3 (0)| 00:00:01 | |* 1 | TABLE ACCESS FULL| MEMBER | 2 | 24 | 3 (0) | 00:00:01| -------------------------------------------------------------------- Predicate Information (identified by operation id): --------------------------------------------------- PLAN_TABLE_OUTPUT -------------------------------------------- 1 - filter(―CAREA‖=‘Allenbury‘) 17 rows selected. The above plan indicates that FULL access is done on the Member table. We can also see the COST of executing the statement (COST=3), expected number of rows to be returned and how many bytes of output will be returned. Case 2. Let us create an index on the cArea column and re-execute the SQL statement. SQL> CREATE INDEX myindex ON Member(cArea); Index created. SQL> EXPLAIN PLAN 2 FOR 3 SELECT cArea FROM Member WHERE cArea=‘Allenbury‘; © SQL Star International Ltd. 360
  • 364. Explained. SQL> @<Oracle_home>RDBMSadminutlxpls.sql PLAN_TABLE_OUTPUT -------------------------------- Plan hash value: 1648515940 --------------------------------------- | Id | Operation | Name | Rows | BytesCos(%CPU)| Time | -------------------------------------------- | 0 | SELECT STATEMENT | | 2 | 24 | 1 (0) |00:00:01 | |* 1 | INDEX RANGE SCAN|MYINDEX | 2 | 24 | 1 (0) | 00:00:01 | --------------------------------------------- Predicate Information (identified by operation id): ----------------------------------------------- PLAN_TABLE_OUTPUT ------------------------------------- 1 - access(―CAREA‖=‘Allenbury‘) 17 rows selected. Here the output very clearly shows that the query uses index access (MYINDEX). Note that the cost of executing the statement (COST=1) is much less here compared to the previous case. Sequences A sequence is a database object used to automatically generate sequential integers for primary key columns. Sequences generate and store numbers, which are not dependent on any particular table. Hence, sequences can be applied to any table that requires a unique identifier for each row. The purposes of generating sequences are:  The integer values are automatically generated by an internal Oracle server routine and therefore, time is saved that would have been otherwise required to write a sequence generating application code.  Sequences that are generated are independent of any table. Therefore, multiple users can use the same sequence. © SQL Star International Ltd. 361
  • 365. Sequences are most commonly used to populate those primary keys that are not used for accessing data stored in tables. This is because there are drawbacks associated with generating sequences to populate primary key columns. For example, the IDs assigned to members, help to identify them as being unique from one another. But if these unique IDs are created by sequences, they could result in some gaps in the sequential values generated, thereby rendering the primary key values meaningless. These gaps in sequences result in the following circumstances:  If inserting sequence-generated values into the primary key column fails, the statement gets rolled back and the number is lost.  If there is a system crash while generating sequential numbers, the number is lost.  As the same sequence can be used for multiple tables, each table will have different values for their primary keys. For example, sqSerialNo sequence is used for inserting ten rows into the Book table. By doing so, its primary key would have the values from 1 to 10. Later, if the same sequence were used to insert ten rows into the Member table, its primary key would have values beginning from 11 to 21. This shows that any subsequent use of the same sequence by the Book or the Member table would generate different value Using Sequences You can create sequences based on some rules and clauses. These help the sequences to generate unique integers in a special order. You can also ensure that their performance is optimized. Creating Sequences The syntax to create a sequence is as follows: CREATE SEQUENCE sequence [START WITH n] [INCREMENT BY n] [(MAXVALUE n | NOMAXVALUE)] [(MINVALUE n | NOMINVALUE)] [(CYCLE | NOCYCLE)] [(CACHE n | NOCACHE)]; Where, sequence is the name of the sequence that will generate the numbers. © SQL Star International Ltd. 362
  • 366. START WITH n is the first value that the sequence generates. INCREMENT BY n is the value with which each integer of the sequence will be incremented. If you do not specify a value the default incrementing value is 1. MAXVALUE n is the value that is the highest integer to be generated by the sequence. If you do not want a maximum limit you can use the NOMAXVALUE option. NOMAXVALUE is 10^27 in ascending and –1 for descending sequences. The latter figure is the default value. MINVALUE n is the value that is the lowest integer to be generated by the sequence. You can use the NOMINVALUE option if you do not want to specify any minimum value. This value is ‗1‘ in case of an ascending value and 10^27 in case of descending value. CYCLE | NOCYCLE allows you to specify if you want the sequence to continue generating numbers after reaching the maximum or minimum values. The numbers generated are recycled. For instance if the minimum value is ‗1‘ and the maximum is ‗10‘ and you specify CYCLE then the 11th number will be ‗1‘ and so on. Specify NOCYCLE if you do not want the numbers to continue being generated. CACHE n | NOCACHE respectively is specified if you want or do not want some values to be pre-allocated and stored in memory by the server. By default 20 values are cached. The syntax clearly shows that there are many rules available that allow developers to define how the sequence numbers are to be generated. For instance, the library database developer decides to create a sequence that generates serial numbers, which could be made use of by any user for any table. The following code illustrates the creation of this sequence: CREATE SEQUENCE sqSerialNo START WITH 1 INCREMENT BY 1 MAXVALUE 1000; On the successful execution of the above code, you get the following message: Sequence created. Viewing Sequence Information Like other database objects, information about sequences is also stored in the system in a data dictionary. © SQL Star International Ltd. 363
  • 367. You can view and confirm the information on the structure of a sequence by using the USER_SEQUENCES data dictionary. The structure of USER_SEQUENCES can be verified by issuing the DESCRIBE command. DESCRIBE USER_SEQUENCES Displays: Name Null? Type ------------ --------- --------- SEQUENCE_NAME NOT NULL VARCHAR2(30) MIN_VALUE NUMBER MAX_VALUE NUMBER INCREMENT_BY NOT NULL NUMBER CYCLE_FLAG VARCHAR2(1) ORDER_FLAG VARCHAR2(1) CACHE_SIZE NOT NULL NUMBER LAST_NUMBER NOT NULL NUMBER You can retrieve the minimum and the maximum values specified for the sequences, along with their incremental values by querying USER_SEQUENCES as shown below. SELECT SEQUENCE_NAME,MIN_VALUE, MAX_VALUE,INCREMENT_BY,LAST_NUMBER FROM USER_SEQUENCES; Displays the following result: SEQUENCE_NAME MIN_VALUE MAX_VALUE INCREMENT_BY LAST_NUMBER ------------- --------- --------- ------------ ----------- SQSERIALNO 1 1000 1 27 © SQL Star International Ltd. 364
  • 368. Using NEXTVAL and CURRVAL After you have created a sequence, you need to be able to view the values in it. To query data from tables with sequences, use the CURRVAL and the NEXTVAL keywords. These keywords represent virtual columns or pseudocolumns. The NEXTVAL pseudocolumn retrieves the next available sequence number from a specified sequence. The CURRVAL pseudocolumn returns the current sequence value that gets generated by NEXTVAL. But to extract the values that NEXTVAL and CURRVAL return, you need to reference them in a SELECT statement issued against the DUAL table. NEXTVAL and CURRVAL are referenced in the SELECT statement by prefixing them with the sequence name. When you pass the command sequence.NEXTVAL, a new number is generated and the current number is stored in CURRVAL. sequence.CURRVAL displays the number that was last returned to the user. When you access NEXTVAL, the value in CURRVAL is the accessed value of NEXTVAL and the previous value in CURRVAL is lost. The values are generated according to some rules that are set when developing the sequence. Given below is a list of restrictions on sequences:  You can only display data from the pseudocolumns and not insert data into them.  Avoid using the pseudocolumns in an INSERT and UPDATE triggers. This action causes the session in which the trigger has been fired to end abnormally.  You cannot use them when selecting from a view.  SELECT statements with the DISTINCT keyword, GROUP BY, HAVING or ORDER BY clauses cannot include these columns.  They cannot be referenced in a DEFAULT expression in a CREATE TABLE or ALTER TABLE statement. You can, however, reference these values in:  The SELECT list of a SELECT statement, which is not part of a subquery  The SELECT list in a subquery used in an INSERT statement  The VALUES clause in an INSERT statement  The SET clause of an UPDATE statement The New Jersey Central Library maintains a table to store details of non-members, that is, those, whose membership has been terminated either due to failure in returning borrowed books after repeated reminders, or those who have terminated © SQL Star International Ltd. 365
  • 369. the membership on their own will. The sequence sqSerialNo can therefore be used for the purpose of inserting rows into the NonMember table as shown below. INSERT INTO NonMember (nSerialNo, cMemberID, cFirstName, cLastName, cPhone,dMembershipDt) VALUES (sqSerialNo.NEXTVAL,‗CAC0989‘, ‗Angela‘,‗Clarke‘,‗9082233‘,‗12-SEP-89‘); 1 row created. To view the current value issue the following statement: SELECT sqSerialNo.CURRVAL FROM DUAL; CURRVAL ----------- 1 Some points that you need to remember while using sequences:  You can access the sequence values faster by caching the values. When a reference is made to the sequence, some values are put into memory. Sequence values are retrieved from the cache each time it is requested. Once the values in cache are over, the next request for a sequence value causes another set of values to be cached.  Gaps in a sequence are not advisable. Sequences are generated in a sequential manner, but incase a ROLLBACK is done, the value is lost. In the event of a system crash the values in cache are lost. Sequences can be used for more than one table and thus in such a case gaps in the sequences will be seen in each table that it is used.  You can view the next value in a sequence without incrementing it, even if you specified NOCAHCE while creating the sequence. Manipulating Sequences You have seen that you can alter a table in case you want to change the definition of some column. Similarly, you can also change the definition of a sequence. In case you want to increase the maximum value of the sequence, you can change its definition to include a higher value. The syntax do so is: ALTER SEQUENCE sequence [INCREMENT BY n] © SQL Star International Ltd. 366
  • 370. [(MAXVALUE n | NOMAXVALUE)] [(MINVALUE n | NOMINVALUE)] [(CYCLE | NOCYCLE)] [(CACHE n | NOCACHE)]; The syntax is the same as that for creating the sequence, but the name used is the name of the sequence already created and needing modification. You can change any parameter of a sequence except the START WITH parameter. Some points to remember when modifying a sequence are:  You need to be the owner of the sequence and have the right to alter it.  You need to be careful when changing a sequence as the future values generated are the ones that are affected by the change.    If you want to change the starting value of the sequence then you need to drop and recreate the sequence as this value cannot be changed using the ALTER SEQUENCE statement.  Care must be taken to ensure not to reset the maximum value to a value lower than the current sequence number. Suppose you have reached the maximum value specified for the sequence sqSerialNo, then the sequence stops generating any additional numbers and displays an error stating that the sequence has surpassed the MAXVALUE. If however, you wish to continue using the sequence, then you need to modify it. But while modifying, if you specify a maximum value lower than the current sequence number generated, you would encounter an error. To view the error, issue the following ALTER SEQUENCE statement: ALTER SEQUENCE sqSerialNo INCREMENT BY 1 MAXVALUE 999; Displays: ALTER SEQUENCE sqSerialNo * Error at line 1: ORA-04009: MAXVALUE cannot be made to be less than the current value. Dropping a sequence © SQL Star International Ltd. 367
  • 371. You can delete a sequence from the data dictionary by using the DROP SEQUENCE statement. The syntax is: DROP SEQUENCE sequence; If the purpose for which the sequence was created has been accomplished, you can remove it. DROP SEQUENCE sqSerialNo; Synonyms You now know how to create various database objects such as tables, views, indexes and sequences. However, when it comes to accessing these objects owned by some other users, then you need to prefix the object names with the names of their owners. This proves to be quite cumbersome especially when the names are lengthy. Hence, an object known as synonyms, which simplifies the accessing of objects owned by other users can be created. Synonyms enable the users to provide alternative names to objects and thereby do away with the need to prefix object names with their owner‘s name. The syntax to give another name to an object is as follows: CREATE [PUBLIC] SYNONYM <synonym_name> FOR <object_name>; Where, PUBLIC specifies that the synonym created can be accessed by all users. synonym_name is the alternative name given to the desired object. © SQL Star International Ltd. 368
  • 372. object_name specifies the object (table, view, sequences or indexes) for which a synonym is to be created. Using Synonyms Synonyms are of two kinds, PUBLIC and PRIVATE. Owners of database objects create private synonyms, especially when their objects have lengthy names, which make them difficult to remember. For instance, ‗Lisa‘ may decide to create a synonym for the vwRandolphBook view created by her. To do so, she would create the following private synonym: CREATE SYNONYM RandolphBk FOR vwRandolphBook; The following message is displayed on successful creation of the sequence: Synonym created. Only the user DBA creates a public synonym, so that it could be accessible to all users. For example, the user DBA decides to create a public synonym for Brad‘s NonMember table as follows: CREATE PUBLIC SYNONYM NonMember FOR Brad.NonMember; After creating a synonym, the user or the user DBA could drop it using the DROP SYNONYM statement. However, only the user DBA can drop a public synonym as follows: DROP SYNONYM BridgetonBk; Synonym dropped. Issuing this statement removes the synonym from the database. © SQL Star International Ltd. 369
  • 373. Summary In this chapter, you have learnt that:  An index is a database object with which you can increase the speed of data  retrieval. Indexes are created automatically when Primary key or Unique key constraints are added to the table. Indexes can also be created manually.  The different types of Indexes are: B-tree index, Bit-map index, Unique index, Non Unique Index, Compressed Index, Function-based index.  EXPLAIN PLAN statement helps us to know the execution details of a particular statement.  Sequence is a database object used to generate automatic numbers. Pseudocolumn NEXTVAL and CURRVAL are used to generate a sequence. A newly created sequence should be first invoked with NEXTVAL. To check the current generated value, use the CURRVAL pseudocolumn.  Once a sequence generates a number, it cannot be rolled back. Also, we cannot use the START WITH clause in the ALTER statement of a sequence.  Synonyms are database objects used to give alternative names to the exisit objects. © SQL Star International Ltd. 370
  • 374. Lab Exercise Create a sequence that can be used with primary key column of the new_dept table. The sequence should start with 200 and have a maximum value of 1000. Name the sequence as NEW_DEPT_ID_SEQ and the sequence should increment by 20. Display the information about your sequence- the sequence name, maximum value, increment size and the last number. 1. Insert three rows into the new_dept table. Use the sequence you created for the deptID column. Add three departments namely, ‗Marketing‘, ‗Administration‘ and ‗Education‘. Confirm whether the rows have been inserted 2. Create an index on the foreign key column of the new_emp table. 3. Display the indexes and the uniqueness that exist in data dictionary table for the new_emp table.   Create a synonym for the new_dept table. © SQL Star International Ltd. 371
  • 375. Chapter 16 Data Dictionary Views Structure of Dictionary Views Purpose of the Dictionary Views Querying Data Dictionary Views © SQL Star International Ltd. 372
  • 376. Objectives At the end of this chapter, you will be able to: Understand available Data dictionaries in Oracle Query Data dictionary Views Understand Dynamic Performance Views v$ © SQL Star International Ltd. 373
  • 377. Data Dictionary A Data Dictionary is nothing but a set of read only tables that provides information about its associated database. It provides information for all types of users right from end users to administrators. It indirectly gets updated under the influence of a DML or DDL Operation. There are hundreds of data dictionary tables and views. These views are built on underlying base tables such as SYS.TAB$. The static data dictionary views contain information about database objects such as tables, indexes and procedures. They are called “static” because the contents of the views change only when DDL operations are executed. For example, a row is added to the USER_TABLES view when any user successfully executes a CREATE TABLE statement. (There are also dynamic views, which we will discuss later in this chapter.) There are three types of static views: 1. USER_ 2. ALL_ 3. DBA_ Where, USER_ level views contain information about the current user’s objects. ALL_ level views contain information about the users objects and objects in other schemas that the user has some privilege on. DBA_ level views are accessed by administrators. Characteristics of Data Dictionaries Following are some of the characteristics of Data Dictionaries:  Cannot be shared across Database(DB) © SQL Star International Ltd. 374
  • 378. Describe the database and objects contained in it Can be accessible with simple SELECT Maintained by the Oracle server Read only Contains Base tables and Data dictionary views A Base table is an internal table, which is automatically created during Database creation. Only Oracle server has the privilege to write it. An example of the base table is the IND$ table, which gets populated while creating indexes for application development. Data Dictionary Contents The tables and views provided by the data dictionary contain information about:  Entire Database structure  Tables and indexes  Integrity Constraints  User Information  Privileges granted on database objects Usage Of Data Dictionaries Data dictionaries are primarily used for Object resolution during any SQL OR PL/SQL operation. For example, SELECT * FROM Member WHERE nAge>6; requires a verification, whether (1) The table Member exists (2) The user has the privilege to access this table (3) The column nAge has been defined for this table etc. © SQL Star International Ltd. 375
  • 379. List of Data Dictionary Views The following SQL command SELECT * FROM DICT[IONARY]; lists all tables and views of the data dictionary that are accessible to the user. The selected information includes the name and a short description of each table and view. Before issuing this query, check the column definitions of DICT[IONARY] using SQL> DESC DICT[IONARY] and set the appropriate values for column using the format command. USER_ DATA DICTIONARY VIEWS This holds the information of the objects created by the user. USER_TABLES: All tables with their name, number of columns, information, statistical information etc. (TABS) USER_COL_COMMENTS: Comments on columns USER_CONSTRAINTS: Constraint definitions for tables USER_INDEXES: All information about indexes created for tables USER_OBJECTS: All database objects owned by the user USER_TAB_COLUMNS : All Columns of the tables and views owned by the user USER_TAB_COMMENTS: Comments on tables and views. USER_TRIGGERS: Triggers defined by the user USER_VIEWS: views defined by the user ALL_ DATA DICTIONARY VIEWS Rows in the ALL views include rows of the USER views and all information about objects that are accessible to the current user. The structure of these views is analogous to the structure of the USER views. ALL_CATALOG: owner, name and types of all accessible tables, views and synonyms ALL_TABLES: owner and name of all accessible tables ALL_OBJECTS: owner, type and name of accessible database objects DBA_ DATA DICTIONARY VIEWS © SQL Star International Ltd. 376
  • 380. The DBA views encompass information about all database objects, regardless of the owner. Only users with DBA privileges can access these views. DBA_TABLES: tables of all users in the database DBA_CATALOG : tables, views, and synonyms defined in the database DBA_OBJECTS : object of all users DBA_DATA FILES: information about data rules DBA_USERS: information about all users known in the database Following is an illustration to use a Data Dictionary View: SELECT OBJECT_NAME, OBJECT_TYPE, CREATED, STATUS FROM USER_OBJECTS; Object_type can be any of the database objects like table, Index, views, synonym, sequence or any objects created in PL/SQL programming like procedures, functions or triggers etc. Created indicates the date of creating the object. Note that a conversion function to_char can be used to get the time. Status indicates whether it is a valid database object or not. Invalid status requires recompilation in certain PL/SQL objects. Note: A view would become invalid, if the underlying base table undergoes any structural change. Below is the output of the above query. ------------------- 45 rows selected. © SQL Star International Ltd. 377
  • 381. Commenting a Table Or Column A table or a column in a table can be provided with comments up to 2000 bytes in 10g. These are registered primarily in 4 data dictionaries for future reference namely,  ALL_COL_COMMENTS  USER_COL_COMMENTS  ALL_TAB_COMMENTS  USER_TAB_COMMENTS In addition to these, there is a dictionary called DBA_TAB_COMMENTS, WHICH is used only by the DBA. To add a comment on the table issue the following command. COMMENT ON TABLE Member IS ‗ To maintain library member information‘; This comment will be recorded in USER_TAB_COMMENTS Dynamic Performance Views V$ These views are virtual tables in which the Oracle server records all the activities happening in a database dynamically. This will reside only in memory and will not occupy any space in any of the schema. V$ views are handled only by administrators to get information such as:  Is the database open?  Is there any session hanging? © SQL Star International Ltd. 378
  • 382.  Is the database performance optimal?  Trouble shooting related information. Examples of V$VIEWS are: V$SESSION: To know the details of a list of users connected to the database. V$SGA: Information regarding Memory V$DATAFILE: List of Datafiles that belong to the database. There are thousands of dynamic performance views available in Oracle. Summary In this chapter, you have learnt that:  A data dictionary is nothing but a set of read only tables that provides information about its associated database. It indirectly gets updated under the influence of a DML or DDL Operation.  Views created on these Data dictionary tables are accessed by the users for retrieving metadata information.  A Data dictionary view can be a static view or a dynamic view. Static views are USER_,(having specific user related information) ALL_,( owned as well as accessible objects information) DBA_(all information accessed by DBA) and dynamic views are V$.(information related to your database) © SQL Star International Ltd. 379
  • 383. Lab Exercise 1. Write a query to check the available tables in your schema. 2. Write a query to see the different objects created in your schema. 3. Display the object names and types from the USER_OBJECTS data dictionary view for the New_Emp and New_Dept tables. 4. Add a comment on the Employees table and view it. 5. Can you access DBA related tables in your schema. If no, what errors do you get? © SQL Star International Ltd. 380
  • 384. Chapter 17 Security Implementation Introduction to user access control Security Model of the Database Creating users Granting system privileges Creating and Managing roles Granting object privileges Query Data Dictionary View for privileges Revoking object privileges © SQL Star International Ltd. 381
  • 385. Objectives At the end of this chapter, you will be able to: Identify the security requirements of a database Identify the database system privileges Create Database Users Change User password for security Create roles to grant privileges to users Grant and revoke object privileges © SQL Star International Ltd. 382
  • 386. Introduction to User Access Control Organizations started using databases due to the huge amounts of data and the functional requirements of accessing the data frequently. But another aspect of organizations is the number of people working there who would access the database regularly. Just as it is important for a bank to keep its money safe with just one or two people permitted to access it, similarly each organization‘s data is critical to them and needs to be handled by the right people. With hundreds of people in the organization accessing the database, security of the database becomes an important issue for the administrators to concentrate on. Methods of Controlling User Access There are various methods by which you can control the user access on the database. They are:  Setting system privileges  Creating roles for users to restrict database access  Setting object privileges  Changing passwords assigned to users  Granting and revoking object privileges  Creating synonyms for database transparency Security Model of the Database Security for the Oracle database is divided into two parts. The first part is the password security provided by the operating system or the Oracle server. The other security model is controlling the access users have to database objects. A database administrator (DBA) or the security administrator for the organization is responsible for the security of the databases. For organizations that are large and work with highly critical data, it is better to have one person dedicated to implement security for the database. Privileges The right to execute particular SQL statements is referred to as privilege(s). The DBA, who is the high-level user, has the power to grant access to the database and its objects, to the users. To gain access to the database, users require system privileges and to manipulate the content of the objects within the database, they require object privileges. © SQL Star International Ltd. 383
  • 387. System Privileges System privileges are certain rights and restrictions that are implemented on the database, so that you can control the access, people have to the database. There are over 100 system privileges available. System privileges are provided typically by the DBA. A few of the typical DBA privileges are listed below. DBA System Privileges Once a DBA creates a user, the DBA can assign specific system privileges to the user. These are known as user system privileges. A few of the typical user privileges are listed below. User System Privileges © SQL Star International Ltd. 384
  • 388. Creating Users The first task that needs to be done is to allow the users to access the database. Only then, will you be able to implement control on their access. To allow people to use the database, you need to create ‗users‘, as are understood by the database. All personnel who have access to use the database will have a different name and password assigned to them. You can create users by using the CREATE USER command. The syntax is: CREATE USER <user> IDENTIFIED BY <{password | externally}>; Where, User is the name you want to give the user Externally is specified when you want the system and database log on to be the same. In this case you need not give a password and when you log on to your machine, you will get connected to the database server without specifying the username and password. Password allows the user to access the database by giving the password specified. An example of creating a user with a password is: CREATE USER LISA IDENTIFIED BY MYDATA; User created. A password is a secret character string, known only to the user. Passwords are set after a user account is created. At first, users are given a default password. They can change it with the following statement. ALTER USER Lisa IDENTIFIED BY bugsbunny User altered. You could also use the PASSWORD command to change the password. The PASSWORD command, when typed, prompts the user for the old password, the new password and confirmation of the new password. The password security does not allow too many attempts in case you have forgotten your password and the account may be locked. It is a good practice to change your password regularly but not too often. When you change your passwords ensure you maintain a history of your passwords so that you do not reuse an old one. There is also a feature that allows you to set the maximum and minimum size of a password. © SQL Star International Ltd. 385
  • 389. The expiry of passwords depends on the profile assigned to your account. Profiles determine the following:  Time period for which a password holds good  Grace period given to change the password  Number of attempts to log on to your account after which the account is locked  Number of days the account is locked  Number of days and other passwords to be used before reusing a password Granting System Privileges to Users System privileges are given with the GRANT command. The syntax is as follows: GRANT privilege [, privilege…] TO user [, user | role, PUBLIC…]; Where, privilege is the system privilege to be granted user | role is the name of the user or role PUBLIC specifies that every user is granted the privilege User ‗Lisa‘ (created in the previous section) could be granted the user system privileges as follows: GRANT CREATE SESSION, CREATE TABLE, CREATE SEQUENCE, CREATE VIEW TO LISA; Grant succeeded. A System privilege that is granted with the WITH ADMIN OPTION clause can be passed on to other users by the grantee. SYSTEM privileges granted with the WITH ADMIN OPTION clause are NOT revoked when the grantor‘s privilege is revoked. © SQL Star International Ltd. 386
  • 390. DBA User1 User2 In the event of DBA revoking the privilege from user1, user2 still enjoys the privilege. Roles So far you have created a user account for ‗Lisa‘ and given her some system permissions. You may create many such user accounts for all the personnel in the organization and give them privileges. But when the size of the database and the organization increases, it will be difficult to manage all the user accounts and the privileges. This makes management of database security more critical. Hence, to make this easier you can create roles. Creating Roles for Database Access A role is the functional part, one plays. For example, an actor or actress performs a role in movies or a person of an organization plays a role like those of a finance manager or marketing executive among many others. When used in relation to a database a role means the same. Many privileges can be grouped under a particular role. This enables easy management of privileges. Roles are also used as virtual privileges. The activities you need to perform to start using roles are: 1. Identifying the similar privileges and grouping them together. 2. Grouping together the various users of the database according to their usage requirements. 3. Create the role. 4. Grant the identified set of privileges to the role. 5. Grant the role to the identified group of users. The syntax for creating a role is: CREATE ROLE <role_name>; Where, role_name is the name assigned to the role to be created. Just as a user name is created with password protection, a role can also be created with password protection. For example, CREATE ROLE MktAnalysis IDENTIFIED BY analyzemarket; © SQL Star International Ltd. 387
  • 391. Role created. The DBA can now assign privileges to the role MktAnalysis using the GRANT statement as follows: GRANT CREATE VIEW TO MktAnalysis WITH ADMIN OPTION; Grant succeeded. The above role MktAnalysis can now be assigned by the DBA to users using the GRANT statement as follows: GRANT MktAnalysis TO Lisa, Maria; Grant succeeded. To assign roles to users, you need to classify the users based on the activities they perform and the privileges they require to perform these activities. Hence based on these, the roles will be granted privileges. The three default roles are:  CONNECT: Enables the users to connect to the database and access data. This role is not assigned the privilege to create tables in the database. The privileges of this role can be further controlled by giving specific rights on tables with different owners and specifying whether the role can perform a query, an insert, update or delete on the tables.  RESOURCE: A role assigned to those users who use the database more regularly. A user with this role has the right to create database objects.  DBA: A role with the highest privileges. The database administrator is responsible for giving and revoking the system privileges from other users and roles. There are two kinds of privileges, DBA and system. DBA privileges are available with the DBA role and system privileges are meant for a DBA user. A DBA also has the rights to export and import the database. For this they are given the roles of EXP_FULL_DATABASE and IMP_FULL_DATABASE. Managing Roles You can alter a role using the ALTER ROLE IDENTIFIED BY statement. You can also delete a role using the DROP ROLE statement. When you drop a role, the user belonging to that role will not have any of the privileges that were attached to the role. To be able to perform these activities you need to have the CREATE ANY ROLE, ALTER ANY ROLE and DROP ANY ROLE privileges. Privileges can be revoked from a role as is done for users using the REVOKE statement. By default, roles are enabled and would have to be disabled explicitly if required. When a role is to be assigned to a user, the required role should be enabled. The ALTER USER DEFAULT ROLE statement needs to be implemented if you want to change the status of the role for a user in any of the following ways: ALTER USER lisa DEFAULT ROLE ALL; ALTER USER lisa DEFAULT ROLE ALL EXCEPT dba; ALTER USER lisa DEFAULT ROLE mktanalysis, statdata; ALTER USER lisa DEFAULT ROLE NONE; © SQL Star International Ltd. 388
  • 392. Object Privileges Once you create an object in a database, there might be situations where the object would have to be changed. Not all users are allowed to manipulate database objects. You (the owner) or the administrator have control over the objects and can manipulate it. If a user has the GRANT ANY PRIVILEGE system privilege then he or she can also control the object. To be able to make changes to database objects you need to have privileges on an object. These are called object privileges. Object privileges enable you to perform specific actions on specific objects. Different objects have different privileges granted for it. Following is a list of object privileges and the objects they can be applied to:  ALTER: tables and sequences  DELETE: tables and views  EXECUTE: procedures  INDEX: tables  INSERT: tables and views  REFERENCES: tables  SELECT: tables, views and sequences  UPDATE: tables and views Granting Object Privileges You grant the object privileges mentioned above with the GRANT command. The syntax is as follows: GRANT <object_privilege| ALL> [(columns)] ON <object> TO {user | role | PUBLIC} [WITH GRANT OPTION]; Where, <object_privilege> is one of the object privileges to be granted. ALL is specified when you want to grant all the privileges. columns of a table or view to which privileges are to be granted. ON object, the object on which the privilege is granted. TO {user | role | PUBLIC} specifies that the privilege can be granted to either a user or a role or to all the users .PUBLIC Keyword is used for all users. WITH GRANT OPTION allows the user with the privilege to grant the same to others. © SQL Star International Ltd. 389
  • 393. The syntax of granting Lisa the right to insert data into the Member table is given below. GRANT INSERT ON Member TO Lisa; If you want to restrict the columns that she can update you may give the following command: GRANT UPDATE (vAddress, cPhone) ON Member TO Lisa; Some points to remember about object privileges are:  Object privileges vary for different objects.  Owners of objects have all the privileges associated with the objects.  Users get the privileges for all objects on their schema.  Grantees can either grant the privileges to other users or not grant them to others.  To grant a privilege, you must be the owner of schema or have the WITH GRANT OPTION. When you are granted privilege on an object in another schema, you need to access the object by prefixing it with the name of the schema. For example, ‗Lisa‘ has been given privilege to enter data into the Member table. The Member table is in the schema owned by ‗Jack.‘ So ‗Lisa‘ will have to execute the following statement: INSERT INTO Jack.Member (cFirstName, cLastName) VALUES (‗Sandy‘, ‗Prill‘); Viewing the Privileges You can confirm the privileges granted to users by querying the data dictionaries. Following is the list of data dictionaries that can be queried:  ROLE_SYS_PRIVS to see system privileges granted to roles  ROLE_TAB_PRIVS to see the table related privileges granted to roles  USER_ROLE_PRIVS to see roles accessible by users  USER_TAB_PRIVS_RECD to see object privileges granted on the user objects  USER_TAB_PRIVS_MADE to see object privileges granted to the user  USER_COL_PRIVS_RECD to see the columns on which privileges have been granted  USER_COL_PRIVS_MADE to see the object privileges granted to users on specific columns In case you do not know what privileges you have, you can query these data dictionary views to check the privileges. If you perform an activity for which you do © SQL Star International Ltd. 390
  • 394. not have privileges, the transaction will not be performed and an error message will be displayed. Revoking Privileges You can also revoke privileges from users and roles, by using the REVOKE statement. The syntax for revoking is as follows: REVOKE <object_privilege, object_privilege, …| ALL> [(columns)] ON <object> FROM {user, user, . . . | role | PUBLIC} [CASCADE CONSTRAINTS] While revoking, you can revoke more than one privilege from more than one user or role or the public at a time. CASCADE CONSTRAINTS is specified if you want to remove any integrity constraints that come with granting the REFERENCES privilege. If there has been a chain of grants enabled by the WITH GRANT OPTION from user to user, then when the owner revokes the privilege from a user who in turn granted the privilege, the revoking has a cascading effect on all the privileges granted. Look at the diagram shown below. User 1 User 2 User 3 When User1 revokes the SELECT privilege from User2, then the privilege granted to User3 by User2 is also revoked. © SQL Star International Ltd. 391
  • 395. Summary In this chapter, you have learnt that:  Restrictive access to the database is implemented by PRIVILEGES. Privileges can be divided into SYSTEM privileges and OBJECT privileges.  SYSTEM privileges are given by the DBA to create database objects. OBJECT privileges are given by the users to another user to manipulate database objects.  PRIVILEGES can be given individually or through ROLES. Role is a schema object containing collection of privileges that can be given to the users.  PRIVILEGES are given to the user by GRANT command and taken back by REVOKE command. © SQL Star International Ltd. 392
  • 396. Lab Exercise [Note: For this Lab exercise, you need to team up with other students in order to implement controlling access to database objects.] 1. Grant query access on your Employees table to another user. (Assume you are user1) In turn have the user (Assume the user to be as user2) grant query access on his/her Employees table to you (user1). 2. Have user1 and user2 insert the following data into their respective Employees table: user1 : Should add 500 as employee ID, Nancy and Win as the first name and last name respectively, nwin@somemail.com as the email ID, 15-Mar- 2002 as the hire date and ST_CLERK as the job ID. user2 : Should add 501 as employee ID, Brown and Rhodes as the first name and last name respectively, Brown@mailme.com as the email ID, 15-Mar- 2002 as the hire date and ST_CLERK as the job ID. Will user1 be able to view the new row inserted by user2 on querying user2.Employees table? Similarly, will user2 be able to view the new row inserted by user1 on querying user1.Employees table? Why? How can they view the new rows inserted by one another? 3. Have user1 create a synonym user2 for user2.Employees table and have user2 create a synonym user1 for user1.Employees table. 4. As a DBA, how would you grant CREATE TABLE, CREATE SEQUENCE and CREATE VIEW privileges to user1 and user2. Since, the same set of system privileges are to be granted to both the users, is there any way to make your job easier? What is the way? 5. Have the users revoke the SELECT privilege on their respective Employees table. © SQL Star International Ltd. 393
  • 397. Chapter 18 Manipulating Large Data Sets Overview of Multi-table INSERT Statements Creating Directories Creating and querying External Tables Unloading Data Using External Table Performing DML with Merge Statement Using FlashBack Enhancement © SQL Star International Ltd. 394
  • 398. Objectives At the end of this chapter, you will be able to: Perform Multi-table Inserts Create Directories Creating and querying External tables Perform DML with Merge Statements Tracking changes in DML using VERSION clause © SQL Star International Ltd. 395
  • 399. Introduction Multi-table INSERT, a feature introduced in Oracle9i, allows you to insert rows into multiple tables as a part of a single DML statement. Multi-table INSERT statements were especially designed with regard to data warehousing system. To facilitate business analysis efficiently, data warehouses must be updated regularly. Multi-table INSERT statements can be used in data warehousing systems to transfer data from one or more operational sources to a set of target tables. Prior to Oracle9i, this was done with independent INSERT…SELECT statements. However, this approach was not only cumbersome, but also created a heavy load on the Oracle server. Multi-table INSERTs perform better than:  Multiple INSERT……SELECT statements  A procedure to do multiple inserts using IF…THEN syntax There are four types of Multi-table INSERT statements:  Unconditional INSERT  Conditional INSERT ALL  Conditional INSERT FIRST  Pivoting INSERT Multi-table INSERT Statement has the following syntax: INSERT [ALL] [conditional_insert_clause] [insert_into_clause values clause] (subquery) The syntax for conditional_insert_clause is: [ALL] [FIRST] [WHEN condition THEN] [insert_into_clause values clause] ELSE [insert_into_clause values clause] Unconditional INSERT In an unconditional Multi-table insert statement, there is no restriction on the insertion of rows into different tables. There may be restriction on the rows that are retrieved in the subquery. You must specify ALL followed by multiple insert_into_clause to perform an unconditional Multi-table insert. The Oracle server executes each insert_into_clause once for each row returned by the subquery. © SQL Star International Ltd. 396
  • 400. For example, to insert details of members who were issued books before 1 st January 2001 and details of books issued before 1st January 2001, use an unconditional Multi-table INSERT statement. First create two tables, namely:  TransMemberHistory, that holds the transaction details of members who were issued books before 1st January‘ 2001. The TransMemberHistory table contains columns to store transaction ID, member ID, book ID, issue date and fine amount. TransBookHistory, that holds the details of books issued before 1 st January‘ 2001. It contains columns to store transaction ID, book ID, issue date, actual return date and fine amount. To perform Multi-table insert into TransMemberHistory and TransBookHistory tables, issue the following query: INSERT ALL INTO TransMemberHistory VALUES (cTranID, cMemberID, cBookID,dIssueDt, nFine) INTO TransBookHistory VALUES (cTranID, cBookID, dIssueDt, dActualReturnDt, nFine) SELECT cTranID, cMemberID, cBookID, dIssueDt, dActualReturnDt, nFine FROM Transaction WHERE dIssueDt<‘01-JAN-2001'; 50 rows created. In the query, first the transaction details before ‗1st Jan, 2001‘ are retrieved from the Transaction table. Then, using INSERT ALL statement, the respective values are inserted into TransMemberHistory and TransBookHistory tables. No condition is specified in the INSERT ALL statement, hence known as unconditional Multi-table insert statement. Conditional INSERT ALL In conditional INSERT ALL statement, the values to be inserted are filtered based on some condition. Depending on your requirement, you can give a separate condition for inserting values into each table or single condition that applies to all tables. In the TransBookHistory and TransMemberHistory tables, if you wish to insert only the data of those members who are due to pay a fine, you can use the Multi- table conditional INSERT ALL statement in the following manner: INSERT ALL © SQL Star International Ltd. 397
  • 401. WHEN nFIne IS NOT NULL THEN INTO TransMemberHistory VALUES (cTranID, cMemberID, cBookID, dIssueDt, nFine) INTO TransBookHistory VALUES (cTranID, cBookID, dIssueDt, dActualReturnDt, nFine) SELECT cTranID, cMemberID, cBookID, dIssueDt, dActualReturnDt, nFine FROM Transaction WHERE dIssueDt<‘01-JAN-2001'; 32 rows created. In the query, first the details of transaction that occurred before ‗1 st Jan, 2001‘ are retrieved by the subquery. Only the details of transactions where a fine amount has to be collected are inserted into the tables TransBookHistory and TransMemberHistory. The condition for selective insert is specified by the WHEN…THEN clauses. As a single insert condition is specified in the above query, it applies to both the tables. You can give separate insert conditions for different tables. Conditional INSERT FIRST Using the conditional INSERT FIRST statement you can insert selective values into multiple tables. Multiple WHEN conditions are specified in this query. However, in INSERT FIRST statement, if the first WHEN condition evaluates to true, the Oracle server executes the corresponding INTO clause, and the subsequent WHEN conditions for this row are skipped. If the first WHEN condition is not true, the subsequent WHEN conditions are evaluated. Wherever the WHEN condition evaluates to true, the corresponding INTO clause is executed. © SQL Star International Ltd. 398
  • 402. For example if you want to perform conditional Multi-table insert using INSERT FIRST statement in the query, first, create the tables TransHistory99, TransHistory00 and TransHistory. Insert the following values in the newly created tables:  The transaction details of all members who are due to pay a fine in TransMemberHistory table  Details of transactions that took place in the year 1999 in table TransHistory99  Details of transactions that took place in the year 2000 in table TransHistory00  Details of transactions that took place in the years other than 1999 and 2000 in table TransHistory The following query performs Multi-table insert into the tables TransMemberHistory, TransHistory99, TransHistory00 and TransHistory using INSERT FIRST statement. INSERT FIRST WHEN nFine IS NOT NULL THEN INTO TransMemberHistory VALUES (cTranID, cMemberID, cBookID, dIssueDt, nFine) WHEN dIssueDt LIKE (‗%99%‘) THEN INTO TransHistory99 VALUES (cTranID, cMemberID, cBookID, dIssueDt, dActualReturnDt) WHEN dIssueDt LIKE (‗%00%‘) THEN INTO TransHistory00 VALUES (cTranID, cMemberID, cBookID, dIssueDt, dActualReturnDt) ELSE INTO TransHistory VALUES (cTranID, cMemberID, cBookID, dIssueDt, dActualReturnDt) SELECT cTranID, cMemberID, cBookID, dIssuedt, dActualReturnDt, nFine FROM Transaction; 32 rows created. Pivoting INSERT Suppose you retrieve a record from a non-relational database table and wish to store it in a relational format, you can do so with the help of an operation called Pivoting INSERT. Pivoting INSERT enables you to transform records retrieved from a non- © SQL Star International Ltd. 399
  • 403. relational database table into a relational format. This is done by converting the retrieved record into multiple records and storing it in a manner that resembles a relational database table environment. For instance, the table StudentMarksDetail contains the details of marks scored by students in all courses. It is a non-relational database table. When you select records from this table, it gives the following output: NSTUDENTNO CCOURSEID NOPSYS NBDMS NARTINT NPROGLANG ---------- --------- ------ ----- ------- --------- 101 SE01 80 75 85 90 As this record is retrieved from a non-relational database table, you can give it a relation format by implementing Pivoting INSERT on it. Because of pivoting INSERT, the marks for each subject in the course will be inserted as a separate row in the StudentMarksInfo table. First create another table called StudentMarksInfo that contains columns for student number, course ID and marks. Following is the query to perform Pivoting INSERT: INSERT ALL INTO StudentMarksInfo values (nStudentNo, cCourseID, nOpSys) INTO StudentMarksInfo values (nStudentNo, cCourseID, nBDMS) INTO StudentMarksInfo values (nStudentNo, cCourseID, nArtInt) INTO StudentMarksInfo values (nStudentNo, cCourseID, nProgLang) SELECT nStudentNo, cCourseID, nOpSys, nBDMS, nArtInt, nProgLang FROM StudentMarksDetail; 4 rows created. When you execute this query, the student marks details are selected from the non- relational database table StudentMarksDetail. The marks of the students in each subject as operating systems, DBMS, Artificial Intelligence and programming languages are inserted as separate records in StudentMarksInfo table. Thus, the output from a non-relational database table is converted into a relational format. When you select records from StudentMarksInfo table, following is the output: NSTUDENTNO CCOURSEID MARKS ——————— ——————— ————— 101 SE01 80 101 SE01 75 101 SE01 85 101 SE01 90 Points to Remember: - © SQL Star International Ltd. 400
  • 404. Multi table inserts can only be performed on tables, not on views or materialized views.  You cannot perform Multi-table inserts into nested tables.  The sum of all the INTO columns cannot exceed 999.  Sequences cannot be used in the subquery of the multi-table insert statement. External Tables External tables are read-only tables. Here data is actually stored outside the database in flat files and only the metadata is stored in the database. If you want to make a table as read-only, create it as an external table. The Oracle server uses drivers to access the data from external files (stored outside the database). However, with external tables you can perform only SQL queries. You cannot perform DML operations (UPDATE/INSERT/DELETE) on external tables, nor can you create indexes on them. To access external tables, Oracle server provides two main access drivers:  ORACLE_LOADER, for reading data from external table using the Oracle loader technology.  ORACLE_INTERNAL, the import/export access driver used for importing and exporting of data using a platform independent format. The data used by external tables is stored in data files stored under a directory. Therefore, you must create a DIRECTORY object that corresponds to the directory on the file system on which the data files reside. The syntax to create a directory object is: CREATE [OR REPLACE] DIRECTORY AS ‗path_name‘; Where, CREATE, Allows you to create a new directory database object REPLACE, Allows you to re-create or replace a directory object DIRECTORY, Name of the directory object to be created, with a maximum length of 30 bytes. You cannot specify a schema name to a directory object. ‗path_name‘ Specifies the full path name of the directory on the server where the data files are located. Single quotes indicate that the path name is case sensitive. As the above command indicates, the ‗path_name‘ is an alias for the directory object. Whenever this directory object is referenced, it actually refers to path where the data files are located. © SQL Star International Ltd. 401
  • 405. Create a directory object mem_dir in the following manner: CREATE DIRECTORY mem_dir AS ‗ext_dat‘; The directory object mem_dir specifies an alias for the directory on the file system of the server, where the data files are stored. Now create a data file called Members.txt containing the data about old members of New Jersey Central Library in the following format :– A01010101,Anna,Jones,25-Nov-1995 B02020202,Steve,Patterson,05-Oct-1994 C03030303,Mark,Blair,12-Jan-1996 Observe the data in the file. The fields are delimited by a ‗,‘ and the records are terminated by new-line. Save this file in the path ‘ext_datMembers.txt’. To convert this datafile into a datasource for external tables, follow these steps: 1. You must first create three directory objects  The default directory object as follows: CREATE OR REPLACE DIRECTORY memdir AS ‗d:ext_data‘;  The log file directory object as follows: CREATE OR REPLACE DIRECTORY log_memdir AS ‗d:ext_data‘;  The bad file directory object as follows: CREATE OR REPLACE DIRECTORY bad_memdir AS ‗d:ext_data‘; © SQL Star International Ltd. 402
  • 406. 2. Grant appropriate read – write permissions to the files stored in these directories  Only read permission to default directory: GRANT READ ON DIRECTORY memdir TO scott;  Write permission to ‗log‘ and ‗bad‘ directories: GRANT WRITE ON DIRECTORY log_memdir TO scott; GRANT WRITE ON DIRECTORY bad_memdir TO scott; 3. Connect to the user scott/tiger and create the external table. CONNECT scott/tiger; Creating External Tables Creating an external table is similar to creating a regular table, except for some additional clauses. You must incorporate the following clauses in your code:  CREATE TABLE clause with column names and their datatypes.  ORGANIZATION EXTERNAL to indicate that the table is an external table and must be stored outside the database.  The access driver type to indicate which driver will be used by the Oracle server to access data from data files.  The DEFAULT DIRECTORY clause, that lets you specify one or more directory objects that correspond to the directories on the file system where the data files are stored. You can specify multiple default directories, as these are permitted to facilitate load balancing.  ACCESS PARAMETERS, which are values specific to the access drivers used for this external table. These values are not interpreted by Oracle but by the access driver used to access data files.  The LOCATION clause that allows you to specify one external locator (usually a data file) for each external data source. The access driver interprets this information and not the Oracle server.  The PARALLEL clause specifies the number of execution servers to simultaneously scan the external data sources (files) during the execution of INSERT INTO TABLE statement.  The REJECT LIMIT specifies how many conversion errors can occur while querying an external data before the Oracle server returns an error message and the query is aborted. By default, the REJECT LIMIT is zero. The following code illustrates the use of all the aforesaid clauses and creates an external table known as OldMembers: CREATE TABLE OldMembers © SQL Star International Ltd. 403
  • 407. (cMemberID char(9), cFirstName CHAR(20), cLastName CHAR(20), dMembershipDt DATE ) ORGANIZATION EXTERNAL ( TYPE ORACLE_LOADER DEFAULT DIRECTORY memdir ACCESS PARAMETERS ( RECORDS DELIMITED BY NEWLINE BADFILE bad_memdir:‘memXt%a_%p.bad‘ LOGFILE log_memdir:‘memXt%a_%p.log‘ FIELDS TERMINATED BY ‗,‘ MISSING VALUES ARE NULL (cMemberID CHAR, cFirstName CHAR, cLastName CHAR, dMembershipDt CHAR date_format date mask ―dd-mon-yyyy‖ ) ) LOCATION (‗Members.txt‘) ) PARALLEL 5 REJECT LIMIT 200; In the above code, the Keywords ORGANIZATION EXTERNAL indicates that the table to be created is an external table which stores data for member ID, first name, last name and membership date. TYPE ORACLE LOADER specifies the access driver. The default directory is memdir. The code also specifies the log directory and the bad directory. The ACCESS PARAMETERS specify the format of the data file. LOCATION specifies the name of the flat file where the data is actually stored. PARALLEL 5 specifies that five server process can simultaneously execute. The REJECT LIMIT is 200, indicating that 200 errors can occur before the query is aborted. When you execute the above code successfully, it creates the external table OldMembers. Table created. © SQL Star International Ltd. 404
  • 408. Now when select the data from external table OldMembers, the driver ORACLE_LOADER looks for the data file Members.txt in the path ‘d:ext_data’ specified by the default directory memdir, fetches the data from Members.txt file and displays it as follows: CMEMBERID CFIRSTNAME CLASTNAME DMEMBERSH --------- ---------- --------- --------- A01010101 Anna Jones 25-NOV-95 B02020202 Steve Patterson 05-OCT-94 C03030303 Mark Blair 12-JAN-96 Unloading Data Using External Tables in Oracle10g Oracle10g has taken external tables a stage further by enabling an external table to be created as a CTAS ( Create Table As Select ) operation, which enables a one-time unloading of data. Oracle has in fact supplied a new access driver known as ―ORACLE_DATAPUMP‖ which means that Oracle will ―unload‖ an external table to a proprietary format usable by the Data Pump set of utilities (significant new 10g feature to replace imp and exp). So, generating an ASCII, CSV file from external tables is not possible, but this new feature is exciting nonetheless. The above feature is demonstrated with a sample example below. Step 1: Create a directory SQL> CREATE DIRECTORY mydir AS ‗/oracle/opt‘; Step 2: Provide permission to one of the users say scott. SQL> GRANT READ, WRITE ON DIRECTORY mydir TO scott; Step 3: Create the external table. CREATE TABLE demotab ORGANIZATION EXTERNAL (TYPE ORACLE_DATAPUMP default directory mydir LOCATION (‗book_category.exp‘)) AS SELECT b.cBookname, b.cAuthorname, c.cCategoryname from Book b, Category c WHERE b.cCategoryid=c.cCategoryid; and we will find a file generated book_category.exp in ‗/oracle/opt‘ directory. We can take this file to the target database and create an external table for that. Merging Rows © SQL Star International Ltd. 405
  • 409. Merging rows enables you to use the UPDATE and INSERT statements in the same query. The MERGE statement (also called ―upsert‖) is an extension of the existing SQL statements. The MERGE statement allows you to conditionally update and insert rows in a table. If the row exists, it updates it, else, inserts it into the table. You can perform these activities using PL/SQL loops and multiple DML statements. However, MERGE is easier to use and can be written as a single SQL statement. The MERGE statement avoids the use of multiple UPDATE statements, requiring few scans of the source table, and thereby improving performance. This concept is particularly useful in data warehousing, where data may be inserted from multiple sources. There can be duplicates. If the row exists, it will be updated, else it will be added. For MERGE statements, you need two tables, a source table and a target table. Using MERGE, you can not only update the values in the target table with the values in the source table but also add new rows from the source to the target table. You must have the INSERT and UPDATE object privileges on the target table and the SELECT object privilege on the source table. To specify the DELETE clause of the merger_update_clause, you must also have the DELETE object privilege on the target table. The MERGE statement is deterministic. You cannot update the same row of the target table multiple times in the same MERGE statement. For instance, if you wish to update the phone numbers in the Member table (target), with the phone numbers in the MemberSrc table (source), use the query given below. The MemberSrc table contains a new row for member ‗Allen Scott‘. The Member table does not contain this row. When you issue a MERGE statement, the new row is inserted into the Member table. This is the advantage of using a MERGE statement, where you can update and insert the rows using a single query. You need not use multiple queries. MERGE INTO Member M USING Membersrc S ON (m.cMemberID = S.cMemberID) WHEN MATCHED THEN © SQL Star International Ltd. 406
  • 410. UPDATE SET m.cPhone=s.cPhone WHEN NOT MATCHED THEN INSERT VALUES(s.cMEmberID, s.cFirstName, s.cLastName, s.vAddress, s.cArea, s.cZipcode, s.cPhone, s.nAge, s.dMembershipDt, s.cGrade, s.cMaritalStatus, s.cBranchID); In the query, first the member IDs of the source and the target are matched. If they match, the phone number in the Member table is updated with the values in the MemberSrc table. If the member IDs do not match (meaning the row does not exist), the row is inserted into Member table. In Oracle10g use of WHEN MATCHED AND WHEN NOT MATCHED clause is made optional. Also, you can restrict the values while inserting into target table using WHERE CLAUSE. For example the above can be slightly modified to insert only those members whose age is greater than 10. MERGE INTO Member M USING Membersrc S ON (m.cMemberID = S.cMemberID) WHEN NOT MATCHED THEN INSERT VALUES(s.cMEmberID, s.cFirstName, s.cLastName, s.vAddress, s.cArea, s.cZipcode, s.cPhone, s.nAge, s.dMembershipDt, s.cGrade, s.cMaritalStatus, s.cBranchID) WHERE S.NAGE>10; Oracle10g Flashback enhancements Oracle 10g provides two enhancements to flashback query, namely, 1. Flashback version query 2. FLASHBACK_TRANSACTION_QUERY VIEW The flashback version query feature let‘s us see the table data as it changed over time. We request the 10g database to show us all versions between two points in time (in the form of time stamps) or between the two system change numbers (SCN‘s). This feature requires that the undo records for the transaction that changed the table data are available. The concept of a ‗version‘ of a row is transaction based. A version is created when a transaction involves row commits. So, if there have been 10 transactions that © SQL Star International Ltd. 407
  • 411. changed the row and 8 were committed – between yesterday and today, and you request all versions of that row in that time period, you will see 8 rows of output- one for each version. Changes that were rolled back do not generate a version. Use the VERSIONS BETWEEN CLAUSE to code a ―flashback version query‖. Oracle 10g supports MINVALUE and MAXVALUE in the VERSIONS BETWEEN clauses. These expressions give access to the oldest and most recent data available. Example of the flashback version query SELECT nFine FROM Transaction WHERE cTranid=‘T0000290100‘; Assume the output gives 15 UPDATE Transaction SET nFine=nFine+0.10 WHERE cTranid=‘T0000290100‘; Now nfine is 15.1. Now commit the above transactions using COMMIT command. Now execute the following statement: SELECT nFine FROM Transaction VERSIONS BETWEEN SCN MINVALUE AND MAXVALUE WHERE cTranid=‘T0000290100‘; Now the output will be 15 and 15.1. FLASHBACK_TRANSACTION_QUERY VIEW It is easy to see the changes made to the tables with flashback_transaction_query view. This can be helpful for auditing (i.e. who changed my table), debugging and even performance analysis (how often is a table being changed). The SELECT ANY TRANSACTION privilege allows the user to query the past transaction by querying the above-mentioned view. © SQL Star International Ltd. 408
  • 412. Summary In this chapter, you have learnt that:  Multi-table insert allows you to insert rows into multiple tables as a part of a single DML statement. These are designed with regard to data warehousing system. There are four types of Multi-table INSERT statements: Unconditional INSERT Conditional INSERT ALL Conditional INSERT FIRST Pivoting INSERT  External tables are read only tables whose data is stored in a flat file. It stores only the metadata information in the database.  MERGE statement is used to perform the insertion and updation as a single operation in the same statement. In Oracle10g, condition merging can be performed.  The flashback version query feature let‘s us see the table data as it changed over time.  FLASHBACK_TRANSACTION_QUERY VIEW helps us to get information for auditing, debugging and statistic analysis. © SQL Star International Ltd. 409
  • 413. Lab Exercise [Note: For questions 1 to 2, you are required to work with SalHistory, ManagerHistory, SpecialSalary, SpecialSalHistory, HireDt00, HireDt99 and HireDt_History tables.] To work with these tables, you need to run the script file LabEx18_01.sql. The structures of these tables are given below. Structure of SalHistory Structure of ManagerHistory Structure of SpecialSalary Structure of SpecialSalHistory Structures of HireDt00, HireDt99, and HireDt_History are the same © SQL Star International Ltd. 410
  • 414. 1. Write a query to retrieve the employee ID, manager ID, hire date, and salary of those employees whose employee ID is less than or equal to 115. Use the query result set to do the following:  Insert into the SpecialSalary table the employee ID and salary of those employees who earn a salary of more than $15,000. In case salary is less than 15,000, do the following:  Insert into the SalHistory table the employee ID, hire date, and salary.  Insert into the ManagerHistory table the employee ID, manager ID, and salary. Confirm the rows created in all the three tables. 2. Write a query to retrieve the department ID, sum of salary, and maximum hire date, which are grouped according to the department ID. Use the result set to perform the following:   Insert department ID and salary into the SpecialSalHistory table if the sum of salary happens to be greater than $20,000. Use conditional FIRST Multi-table INSERT.   In case the first WHEN clause returns TRUE, skip the subsequent WHEN clauses for this row.  In case of the rows that do not satisfy the first WHEN clause, insert into:   HireDt00 table if hire date year is 2000   HireDt99 table if hire date year is 1999   HireDt_History table for all other hire dates Confirm the rows created in the above tables. [Note: For question 3, you are required to work with SalesInfoFile and SalesInfo tables.] 3. To create these tables run the script file LabEx18_03.sql. To insert records into the SalesInfoFile table run the script file LabEx18_03a.sql. Structure of SalesInfoFile © SQL Star International Ltd. 411
  • 415. SalesInfoFile table data Structure of SalesInfo Write a query to retrieve the employee ID, week ID, and sales figures on Monday, Tuesday, Wednesday, Thursday, and Friday from the SalesInfoFile table such that the records retrieved are converted into multiple records for the SalesInfo table. Confirm the records inserted into SalesInfo table. 4. Create an External Table called All_objects_Xt, dump data into a .txt file. Select the data from all_objects data dictionary. Query the external table 5a. Create a table Tax with the below given two columns: Salary NUMBER(10) Tax_Rate NUMBER(15,5) 5b. Insert 1 row into them with values 20000,10. Commit it Update the Tax_rate with 0.15. Commit it Increase the Tax_rate further with 0.20. Commit it Delete the row from the table. Commit it Insert 1 row into the table with values 20000,25. Commit it Update the Tax_rate with 0.27. © SQL Star International Ltd. 412
  • 416. Commit it 6. Write a query to select the prevailing tax rate from the table. 7. Write a query to list all the changes made to the Tax table. What enhancement has been made in External table. © SQL Star International Ltd. 413
  • 417. Chapter 19 REGULAR EXPRESSION Overview of Regular Expression Support List of Meta-characters Regular Expression Functions © SQL Star International Ltd. 414
  • 418. Objectives At the end of this chapter, you will be able to:  Use meta-characters  Use regular expression functions  Use NOVALIDATE Clause © SQL Star International Ltd. 415
  • 419. Introduction to REGULAR EXPRESSION In Oracle Database 10g, additional meta-characters have been introduced; in an attempt to make the search, compare and replace functions operate in a more intensified manner, than it is in Unix and Java. These functions are known as regular expressions that has made matching complex text pattern more effective. It follows Portable Operating System For Unix (POSIX) standard for matching ASCII characters. With this new feature, most of the complex search requirements of the end users can be addressed. META-CHARACTER These are special characters with pre-defined meaning that are used in our complex string-matching pattern. Following is the list of Meta-Characters that are used for String Searching. © SQL Star International Ltd. 416
  • 420. Below are the various comparisons for the Character class, which is used in complex string searching. © SQL Star International Ltd. 417
  • 421. Regular Expression Functions Oracle Database 10g has come up with 4 new functions which use meta-characters in their arguments to help us accomplish our complex string pattern matching task. The Searched String is to be enclosed in single quotation marks. These functions are primarily an extension to our basic SQL functions with little variations. Following are the list of Functions introduced in Oracle10g: REGEXP_LIKE Looks for a matching pattern in a character column. It takes two arguments. First argument is the name of the character column. Second argument is a regular expression string. Following is an example of the syntax for this function: - REGEXP_LIKE(srcstr, pattern [,match_option]) In this example, ‘ Names of the Members are extracted who have ‗at‘ in their firstname‘. SELECT cFirstName FROM member WHERE REGEXP_LIKE (cfirstname,’(at)’); Displays: CFIRSTNAME ---------- Katya Kathy REGEXP_REPLACE Looks for a matching pattern in a character column and replaces each occurrence of that pattern with the specified pattern. The syntax for this is: REGEXP_REPLACE(srcstr, pattern [,replacestr [, position [, occurrence [, match_option]]]]) In this example, two spaces are replaced by a single space in a string. SELECT REGEXP_REPLACE(‗NEW JERSEY LIBRARY STORES ‗, ‗( ){2,}‘, ‘ ‗) ―REGEXP_REPLACE‖ FROM DUAL; Displays: REGEXP_REPLACE © SQL Star International Ltd. 418
  • 422. ------------ NEW JERSEY LIBRARY STORES REGEXP_INSTR This function searches a string for a given occurrence of a regular expression pattern. You can specify which occurrence you want to find and the start position. Syntax : REGEXP_INSTR (srcstr, pattern [, position [, occurrence [, return_option [, match_option]]]]) Example given below shows the position of @ in a given email id. SELECT REGEXP_INSTR(email,‘@{1}‘) ―Position‖ FROM MEMBER; Displays: Position -------- 12 REGEXP_SUBSTR This is similar to REGEXP_INSTR but instead of the position of the specified pattern it returns a part of a string after matching the regular expression pattern. Following is the syntax: - REGEXP_SUBSTR (srcstr, pattern [, position [, occurrence [, match_option]]]) Example to extract the username from the email of the members of New Jersey Central Library: SELECT REGEXP_SUBSTR(member_email, ‗[^@]+‘) FROM Member; Explanation for the words used in the Syntax © SQL Star International Ltd. 419
  • 423. Srcstr:- Indicates the Search value that can be an expression or a character column name. Pattern:- Regular expression replacestr:- Character String replacing pattern. Position:- Starting position to Search from. Occurrence:- Number of Occurrences to search for. Return_option:- Beginning or Ending position of occurrence Match_option:-Option to change default matching; it can include one or more of the following values: “c” —uses case-sensitive matching (default) “I” —uses case-insensitive matching “n” —allows match-any-character operator “m” —treats source string as multiple line Validating Data using Constraints These multilingual regular expression functions can be included in CHECK constraint, which prevent invalid data from being entered. To make the checking‘s on the subsequent data only, NOVALIDATE clause can be specified. To check that cMemberid should start with ‗M‘ only, the following code should be executed. ALTER TABLE Member ADD CONSTRAINT e CHECK(REGEXP_LIKE (cMemberid,‗^M‘))NOVALIDATE; Here ‗^M‘ expression checks for the Member id starting with ‗M‘. NOVALIDATE clause ensures that only subsequent entries of data are validated. © SQL Star International Ltd. 420
  • 424. Summary In this chapter, you have learnt that: Regular expression works beyond the Portable Operating System For Unix (POSIX) Standard.  It helps us to perform complex string matching operation.  New meta-character symbols have been introduced for string matching operation.  New Functions such as REGEXP_LIKE(for comparison), REGEXP_REPLACE(for Replacing), REGEXP_INSTR(for finding position of a character), REGEXP_SUBSTR (returns part of a string) are introduced to accomplish our complex string pattern matching task. © SQL Star International Ltd. 421
  • 425. Lab Exercise 1. A string contains three spaces in between. For example ‗NEW DELHI‘. Write a query to replace the spaces with one. The output displayed should be as NEW DELHI 2. Write a query, which extracts a part of a string. The regular expression searches for a comma followed by a space; then zero or more characters that are not commas, as indicated by [^,]*; and lastly looks for another comma. The pattern will look similar to a comma-separated values string. (‗first part, second part, third part‘) 3. Retrieve any values from ename that start with J, followed by any letter, then N or M, then any letter, then S from Emp table © SQL Star International Ltd. 422