Anda di halaman 1dari 15

Scalar Subquery Expressions

A scalar subquery expression is a subquery that returns exactly one column value from one
row. The value of the scalar subquery expression is the value of the select list item of the
subquery. If the subquery returns 0 rows, then the value of the scalar subquery expression
is NULL. If the subquery returns more than one row, then Oracle returns an error.

You can use a scalar subquery expression in most syntax that calls for an expression
(expr). In all cases, a scalar subquery must be enclosed in its own parentheses, even if its
syntactic location already positions it within parentheses (for example, when the scalar
subquery is used as the argument to a built-in function).

You can use a scalar subquery expression in most syntax that calls for an expression
(expr). However, scalar subqueries are not valid expressions in the following places:

As default values for columns

As hash expressions for clusters

In the RETURNING clause of DML statements

As the basis of a function-based index

In CHECK constraints

In WHEN conditions of CASE expressions

In GROUP BY and HAVING clauses

In START WITH and CONNECT BY clauses

In statements that are unrelated to queries, such as CREATE PROFILE

Example of Scalar subquery

SELECT last_name, job_id, salary


FROM employees
WHERE salary > (SELECT avg(salary) FROM employees);
Indexes
An index can be created in a table to find data more quickly and
efficiently.

The users cannot see the indexes, they are just used to speed up
searches/queries.

An index helps speed up SELECT queries and WHERE clauses, but it slows
down data input, with UPDATE and INSERT statements. Indexes can be
created or dropped with no effect on the data.

Creating an index involves the CREATE INDEX statement, which allows you
to name the index, to specify the table and which column or columns to
index, and to indicate whether the index is in ascending or descending
order.

Indexes can also be unique, similar to the UNIQUE constraint, in that the
index prevents duplicate entries in the column or combination of columns
on which there's an index.

The CREATE INDEX Command:


The basic syntax of CREATE INDEX is as follows:

CREATE INDEX index_name ON table_name;

Single-Column Indexes:
A single-column index is one that is created based on only one table
column. The basic syntax is as follows:

CREATE INDEX index_name


ON table_name (column_name);
Unique Indexes:
Unique indexes are used not only for performance, but also for data
integrity. A unique index does not allow any duplicate values to be inserted
into the table. The basic syntax is as follows:

CREATE UNIQUE INDEX index_name


on table_name (column_name);

Composite Indexes:
A composite index is an index on two or more columns of a table. The basic
syntax is as follows:

CREATE INDEX index_name


on table_name (column1, column2);

Whether to create a single-column index or a composite index, take into


consideration the column(s) that you may use very frequently in a query's
WHERE clause as filter conditions.

Should there be only one column used, a single-column index should be the
choice. Should there be two or more columns that are frequently used in
the WHERE clause as filters, the composite index would be the best choice.

The DROP INDEX Command:


An index can be dropped using SQL DROP command. Care should be taken
when dropping an index because performance may be slowed or improved.

The basic syntax is as follows:

DROP INDEX index_name;


You can check INDEX Constraint chapter to see actual examples on Indexes.

When should indexes be avoided?


Although indexes are intended to enhance a database's performance, there
are times when they should be avoided. The following guidelines indicate
when the use of an index should be reconsidered:

Indexes should not be used on small tables.

Tables that have frequent, large batch update or insert operations.

Indexes should not be used on columns that contain a high number of


NULL values.

Columns that are frequently manipulated should not be indexed.

CREATE INDEX Example


The SQL statement below creates an index named "PIndex" on the
"LastName" column in the "Persons" table:

CREATE INDEX PIndex


ON Persons (LastName)

cursor
Oracle creates a memory area, known as context area, for processing an
SQL statement, which contains all information needed for processing the
statement, for example, number of rows processed, etc.
A cursor is a pointer to this context area. PL/SQL controls the context area
through a cursor. A cursor holds the rows (one or more) returned by a SQL
statement. The set of rows the cursor holds is referred to as the active set.

You can name a cursor so that it could be referred to in a program to fetch


and process the rows returned by the SQL statement, one at a time. There
are two types of cursors:

Implicit cursors

Explicit cursors

Implicit Cursors
Implicit cursors are automatically created by Oracle whenever an SQL
statement is executed, when there is no explicit cursor for the statement.
Programmers cannot control the implicit cursors and the information in it.

Whenever a DML statement (INSERT, UPDATE and DELETE) is issued, an


implicit cursor is associated with this statement. For INSERT operations, the
cursor holds the data that needs to be inserted. For UPDATE and DELETE
operations, the cursor identifies the rows that would be affected.

In PL/SQL, you can refer to the most recent implicit cursor as the SQL
cursor, which always has the attributes like %FOUND, %ISOPEN,
%NOTFOUND, and %ROWCOUNT. The SQL cursor has additional attributes,
%BULK_ROWCOUNT and %BULK_EXCEPTIONS, designed for use with the
FORALL statement. The following table provides the description of the most
used attributes:

Attribute Description

%FOUND Returns TRUE if an INSERT, UPDATE, or DELETE statement


affected one or more rows or a SELECT INTO statement
returned one or more rows. Otherwise, it returns FALSE.

%NOTFOUND The logical opposite of %FOUND. It returns TRUE if an INSERT,


UPDATE, or DELETE statement affected no rows, or a SELECT
INTO statement returned no rows. Otherwise, it returns
FALSE.

%ISOPEN Always returns FALSE for implicit cursors, because Oracle


closes the SQL cursor automatically after executing its
associated SQL statement.

%ROWCOUNT Returns the number of rows affected by an INSERT, UPDATE,


or DELETE statement, or returned by a SELECT INTO
statement.

Any SQL cursor attribute will be accessed as sql%attribute_name as


shown below in the example.

Example:
We will be using the CUSTOMERS table we had created and used in the
previous chapters.

Select * from customers;

+----+----------+-----+-----------+----------+
| ID | NAME | AGE | ADDRESS | SALARY |
+----+----------+-----+-----------+----------+
| 1 | Ramesh | 32 | Ahmedabad | 2000.00 |
| 2 | Khilan | 25 | Delhi | 1500.00 |
| 3 | kaushik | 23 | Kota | 2000.00 |
| 4 | Chaitali | 25 | Mumbai | 6500.00 |
| 5 | Hardik | 27 | Bhopal | 8500.00 |
| 6 | Komal | 22 | MP | 4500.00 |
+----+----------+-----+-----------+----------+

The following program would update the table and increase salary of each
customer by 500 and use the SQL%ROWCOUNT attribute to determine the
number of rows affected:

DECLARE
total_rows number(2);
BEGIN
UPDATE customers
SET salary = salary + 500;
IF sql%notfound THEN
dbms_output.put_line('no customers selected');
ELSIF sql%found THEN
total_rows := sql%rowcount;
dbms_output.put_line( total_rows || ' customers selected ');
END IF;
END;
/

When the above code is executed at SQL prompt, it produces the following
result:

6 customers selected

PL/SQL procedure successfully completed.


If you check the records in customers table, you will find that the rows have
been updated:

Select * from customers;

+----+----------+-----+-----------+----------+
| ID | NAME | AGE | ADDRESS | SALARY |
+----+----------+-----+-----------+----------+
| 1 | Ramesh | 32 | Ahmedabad | 2500.00 |
| 2 | Khilan | 25 | Delhi | 2000.00 |
| 3 | kaushik | 23 | Kota | 2500.00 |
| 4 | Chaitali | 25 | Mumbai | 7000.00 |
| 5 | Hardik | 27 | Bhopal | 9000.00 |
| 6 | Komal | 22 | MP | 5000.00 |
+----+----------+-----+-----------+----------+

Explicit Cursors
Explicit cursors are programmer defined cursors for gaining more control
over the context area. An explicit cursor should be defined in the
declaration section of the PL/SQL Block. It is created on a SELECT
Statement which returns more than one row.

The syntax for creating an explicit cursor is :

CURSOR cursor_name IS select_statement;

Life Cycle of Cursor


1. Declare Cursor
A cursor is declared by defining the SQL statement that returns a result set.
2. Open
A Cursor is opened and populated by executing the SQL statement defined
by the cursor.

3. Fetch
When cursor is opened, rows can be fetched from the cursor one by one or
in a block to do data manipulation.

4. Close
After data manipulation, we should close the cursor explicitly.

5. Deallocate
Finally, we need to delete the cursor definition and released all the system
resources associated with the cursor.

Declaring the Cursor


Declaring the cursor defines the cursor with a name and the associated
SELECT statement. For example:

CURSOR c_customers IS
SELECT id, name, address FROM customers;

Opening the Cursor


Opening the cursor allocates memory for the cursor and makes it ready for
fetching the rows returned by the SQL statement into it. For example, we
will open above-defined cursor as follows:

OPEN c_customers;
Fetching the Cursor
Fetching the cursor involves accessing one row at a time. For example we
will fetch rows from the above-opened cursor as follows:

FETCH c_customers INTO c_id, c_name, c_addr;

Closing the Cursor


Closing the cursor means releasing the allocated memory. For example, we
will close above-opened cursor as follows:

CLOSE c_customers;

Example:
Following is a complete example to illustrate the concepts of explicit
cursors:

DECLARE
c_id customers.id%type;
c_name customers.name%type;
c_addr customers.address%type;
CURSOR c_customers is
SELECT id, name, address FROM customers;
BEGIN
OPEN c_customers;
LOOP
FETCH c_customers into c_id, c_name, c_addr;
EXIT WHEN c_customers%notfound;
dbms_output.put_line(c_id || ' ' || c_name || ' ' || c_addr);
END LOOP;
CLOSE c_customers;
END;
/

Stored Procedure: Stored Procedure in SQL Server can be defined as the set of
logical group of SQL statements which are grouped to perform a specific task.
There are many benefits of using a stored procedure. The main benefit of using
a stored procedure is that it increases the performance of the database.The
other benefits of using the Stored Procedure are given below.

Benefits of Using the Stored


Procedure
1. One of the main benefits of using the Stored procedure is that it reduces
the amount of information sent to the database server. It can become a more
important benefit when the bandwidth of the network is less. Since if we send
the SQL query (statement) which is executing in a loop to the server through
network and the network gets disconnected, then the execution of the SQL
statement doesn't return the expected results, if the SQL query is not used
between Transaction statement and rollback statement is not used.
2. Compilation step is required only once when the stored procedure is
created. Then after it does not require recompilation before executing unless it is
modified and reutilizes the same execution plan whereas the SQL statements
need to be compiled every time whenever it is sent for execution even if we
send the same SQL statement every time.
3. It helps in re usability of the SQL code because it can be used by multiple
users and by multiple clients since we need to just call the stored procedure
instead of writing the same SQL statement every time. It helps in reducing the
development time.
4. Stored procedure is helpful in enhancing the security since we can grant
permission to the user for executing the Stored procedure instead of giving
permission on the tables used in the Stored procedure.
5. Sometimes, it is useful to use the database for storing the business logic
in the form of stored procedure since it makes it secure and if any change is
needed in the business logic, then we may only need to make changes in the
stored procedure and not in the files contained on the web server.

Syntax
Following is the basic syntax of Stored procedure creation.

Create procedure <procedure_Name>


As
Begin
<SQL Statement>
End
Go

Example
Consider the CUSTOMERS table having the following records.

ID NAME AGE ADDRESS SALARY


1 Ramesh 32 Ahmedabad 2000.00
2 Khilan 25 Delhi 1500.00
3 kaushik 23 Kota 2000.00
4 Chaitali 25 Mumbai 6500.00
5 Hardik 27 Bhopal 8500.00
6 Komal 22 MP 4500.00
7 Muffy 24 Indore 10000.00

Following command is an example which would fetch all records from the
CUSTOMERS table in Testdb database.

CREATE PROCEDURE SelectCustomerstabledata


AS
SELECT * FROM Testdb.Customers
GO

The SQL GROUP BY clause is used in collaboration with the SELECT


statement to arrange identical data into groups.

The GROUP BY clause follows the WHERE clause in a SELECT statement and
precedes the ORDER BY clause.
Syntax:
The basic syntax of GROUP BY clause is given below. The GROUP BY clause
must follow the conditions in the WHERE clause and must precede the
ORDER BY clause if one is used.

SELECT column1, column2


FROM table_name
WHERE [ conditions ]
GROUP BY column1, column2
ORDER BY column1, column2

Example:
Consider the CUSTOMERS table is having the following records:

+----+----------+-----+-----------+----------+
| ID | NAME | AGE | ADDRESS | SALARY |
+----+----------+-----+-----------+----------+
| 1 | Ramesh | 32 | Ahmedabad | 2000.00 |
| 2 | Khilan | 25 | Delhi | 1500.00 |
| 3 | kaushik | 23 | Kota | 2000.00 |
| 4 | Chaitali | 25 | Mumbai | 6500.00 |
| 5 | Hardik | 27 | Bhopal | 8500.00 |
| 6 | Komal | 22 | MP | 4500.00 |
| 7 | Muffy | 24 | Indore | 10000.00 |
+----+----------+-----+-----------+----------+

If you want to know the total amount of salary on each customer, then
GROUP BY query would be as follows:

SQL> SELECT NAME, SUM(SALARY) FROM CUSTOMERS


GROUP BY NAME;

This would produce the following result:

+----------+-------------+
| NAME | SUM(SALARY) |
+----------+-------------+
| Chaitali | 6500.00 |
| Hardik | 8500.00 |
| kaushik | 2000.00 |
| Khilan | 1500.00 |
| Komal | 4500.00 |
| Muffy | 10000.00 |
| Ramesh | 2000.00 |
+----------+-------------+

Now, let us have following table where CUSTOMERS table has the following
records with duplicate names:

+----+----------+-----+-----------+----------+
| ID | NAME | AGE | ADDRESS | SALARY |
+----+----------+-----+-----------+----------+
| 1 | Ramesh | 32 | Ahmedabad | 2000.00 |
| 2 | Ramesh | 25 | Delhi | 1500.00 |
| 3 | kaushik | 23 | Kota | 2000.00 |
| 4 | kaushik | 25 | Mumbai | 6500.00 |
| 5 | Hardik | 27 | Bhopal | 8500.00 |
| 6 | Komal | 22 | MP | 4500.00 |
| 7 | Muffy | 24 | Indore | 10000.00 |
+----+----------+-----+-----------+----------+
Now again, if you want to know the total amount of salary on each
customer, then GROUP BY query would be as follows:

SQL> SELECT NAME, SUM(SALARY) FROM CUSTOMERS


GROUP BY NAME;

This would produce the following result:

+---------+-------------+
| NAME | SUM(SALARY) |
+---------+-------------+
| Hardik | 8500.00 |
| kaushik | 8500.00 |
| Komal | 4500.00 |
| Muffy | 10000.00 |
| Ramesh | 3500.00 |
+---------+-------------+

Anda mungkin juga menyukai