SQL Server 2005
SQL Server 2005
The SQL Server administrator’s primary tool for interacting with the system is the SQL Server Management
Studio. Not only the Administrators, but also the end-users can use this tool to administer multiple servers,
develop databases, data backup and recovery, etc.
It can be used to manage SQL Sever 2005 systems, as well as, SQL Server 2000 and SQL Server 7
systems, but not SQL Server 6.5 or older SQL systems.
SQL Server Management Studio is made up of several component-windows, the major one’s being:
Registered Servers
It show the list of servers that you manage. You can add to it new servers or one or more existing
servers can be removed from the list. You can also use it to group common servers together into a
logical server group.
Object Explorer
The Object Explorer window contains a tree view of all the database-objects in a server
To us the Object Explorer, click the Connect button on the Object-Explorer toolbar, select Database
Engine and select the name of the server and the connect authentication mode.
To work with the displayed objects, right-click the desired object and select an option from that
objects context-menu.
It allows you to easily create scripts for an entire database, or for a single database object. Expand
the Database folder in the Object Explorer and right-click a database. Select the Tasks option from
the context-menu , and then select the Generate Scripts.
Document Window
When you select an item in Object Explorer, information about that object is presented in a
document window called Summary Page. The Document window can also contain Query Editors
and Browser Windows.
Query Editor
It is the replacement for Query Analyser found in earlier versions. In the query-editor, you
can write and execute T-SQL scripts, MDX, DMX, XMLA queries or mobile queries.
Unlike the Query Analyser, the Query Editor can work either in the Connected or
Disconnected Mode. By default, it automatically connects to the server as soon as you opt
to create a new query.
To view the Query Window/Editor, press CTRL+N or Click the File Menu, New Option,
Query with Current Connection or Click the New Query button in the Standard Toolbar
Results Window
The results of the queries that are executed in the Query Editor are displayed in
the Result’s Window.
Messages Window
The message associated with the executed SQL statement is shown in the
message window
Browser Window
To view the Browser Window, click on the View menu, Web Browser option , Home. This
can be used to browse through Microsoft or other sites, as per requirement.
Solutions Explorer
It provides a Hierarchical tree view of the different projects and files in a solution. A solution
includes one or more projects, files and metadata that define the solution as a whole.
A project is a set of files that contain the connection information, query files, and other
miscellaneous and related metadata files.
The three types of projects you can have in the solutions explorer are :
They are used to group together Data Definition Language(DDL) queries which define the
objects in a database. Also used to group together related SQL Server Connections and
Transact-SQL Scripts.
Properties Window
This window allows you to view properties of files, projects, or solutions in SQL Server
Management Studio. If the properties window is not visible, then you can view it by
selecting Properties Window option from the View menu.
A Properties Dialog Box can also be invoked for the Database Objects, by right-clicking
the database object and selecting Properties from the Context-menu.
DATA TYPES
Numeric Data Types
Use char when the sizes of the column data entries are consistent.
Use varchar when the sizes of the column data entries vary considerably.
Use varchar(max) when the sizes of the column data entries vary considerably, and the size might exceed
8,000 bytes. Max indicates that the maximum storage size is 2^31-1(2147483647) bytes.
VARCHAR(MAX) They allow you to store upto 2^31 - 1 bytes of data. They are
NVARCHAR(MAX) similar in behavior to Varchar, Nvarchar and Varbinary
VARBINARY(MAX) datatypes. They allow you to store and retrieve large character
data, Unicode data, and Binary data respectively with more
efficiency then TEXT, NTEXT and IMAGE data types
respectively.
Numeric Functions
DATE FUNCTIONS:
SELECT GETDATE()
SELECT DATEPART(MONTH,'2007-07-26'),DATEPART(MM,'2007-07-26'), DATEPART(QQ,'2007-07-
26'),DATEPART(QUARTER,'2007-07-26'),DATEPART(YY,'2007-07-26'), DATEPART(YEAR,'2007-07-26');
SELECT DATEPART(DY,'2007-07-26'), DATEPART(DaY,'2007-07-26'),DATEPART(DD,'2007-07-26'),
DATEPART(DW,'2007-07-26'), DATEPART(WK,'2007-07-26');
SELECT DATEPART(HH,GETDATE()), DATEPART(HOUR,GETDATE()),DATEPART(MI,GETDATE()),
DATEPART(MINUTE,GETDATE()), DATEPART(SS,GETDATE()), DATEPART(SECOND,GETDATE()),
DATEPART(MS,GETDATE()), DATEPART(MILLISECOND,GETDATE())
SELECT DATENAME(MONTH, GETDATE()), DATENAME(DW,'2007-07-26'),
DATENAME(WEEKDAY,'2007-07-26')
select DATEDIFF(YEAR,'1976-07-26 23:30:48.986', GETDATE()), DATEDIFF(MM,'1976-07-26
23:30:48.986', GETDATE()), DATEDIFF(QQ,'1976-07-26 23:30:48.986', GETDATE()),
DATEDIFF(DD,'1976-07-26 23:30:48.986', GETDATE()), DATEDIFF(DY,'1976-07-26 23:30:48.986',
GETDATE()), DATEDIFF(DW,'1976-07-26 23:30:48.986', GETDATE()), DATEDIFF(WK,'1976-07-26
23:30:48.986', GETDATE()), DATEDIFF(HH,'1976-07-26 23:30:48.986', GETDATE()), DATEDIFF(MI,'1976-
07-26 23:30:48.986', GETDATE()), DATEDIFF(SS,'1976-07-26 23:30:48.986', GETDATE())
SELECT DATEADD(YEAR,3, GETDATE()), DATEADD(MM,3, GETDATE()), DATEADD(QQ,3,
GETDATE()), DATEADD(DD,3, GETDATE()), DATEADD(WK,3, GETDATE()), DATEADD(HH,3,
GETDATE()), DATEADD(MI,3, GETDATE()), DATEADD(SS,3, GETDATE())
GLOBAL VARIABLES :
INSERT Command
create table table1(c1 numeric default 10, c2 varchar(10), c3 char(10) default 'xyz', c4 numeric(5,2))
This form of INSERT command inserts one row (or parts of it) into the specified Table or Simple View
subject to non-violation of constraints at the table-level. If a column is of datatype TIMESTAMP or has the
IDENTITY property, a value, which is automatically calculated by the system, is inserted
insert into table2(c1,c2) select c1, c2 from table1 where c1 between 102 and 104
insert into table2 select * from table1 where c1 between 102 and 104
UPDATE
Update table_name|view_name
Set col1=value, col2=value, …
From table_name1|view_name1, table_name2|view_name2
WHERE condition(s)
If Jones is ill and on leave then the projid column for all his corresponding rows in the project table shoud be
set to NULL
Update project set projid=null where empno = (select empno from emp where empname=’jones’)
This can also be achieved using the FROM cluase of Update statement as follows :
Update project set projid=nul from emp, project where emp.empname=’jones’ and
project.empno=emp.empno
DELETE
Delete table_name|view_name
FROM table_name1|view_name1, table_name1|view_name1,…
WHERE predicate
Delete table_name|view_name
WHERE condition(s)
delete orders
or
delete from orders
As WHERE cluase is ommitted all the rows are deleted
If Jones is ill and on leave then the all his corresponding rows in the project table shoud be deleted
Delete from project where empno = (select empno from emp where empname=’jones’)
TRUNCATE TABLE table_name normally provides a faster execution version of the delete statement
without a where clause. The Truncate has no WHERE clause. It works faster as it drops the contents of the
table page by page whereas delete does it row by row. Truncate does not place the modifications of a table
into the transaction log.
All databases have one ‘primary’ data-file that has, by default, the same name(logical) as the corresponding
database. The physical name of this file is, by default, suffixed with the extension ‘.mdf’. Optionally, there
can be one or more secondary data files whose physical names are suffixed by the extension ‘.ndf’, by
default. Similarly, each database has one primary log-file, whose default name is dbname_log. Optionally,
there can be additional log files also. All the log files are suffixed by the extension ‘.ldf’. All the suffixes are
recommended extensions, and can be modified if required.
All the data files that are used to store a database’s data an be grouped to build filegroups. With filegropus,
you can locate different tables or indices on a specific file (or set of files).
1) Primary filegroup which is impliciltly created by the system during the creation of the database. All
system tables are always in the primary filegroup, while user-defined tables can belong either to the primary
filegroup or to any user-defined filegroup.
By default, the Primary filegroup is the default filegroup. You may change the default filegroup to any other
user-defined filegroup, if required. The default filegroup indicates the filegroup to be used when no filegroup
is specified as a part of table or index creation.
Creates a database named ‘sample’ with default specifications. SQL Server creates two files for this
database by default. The logical name of the data file is ‘sample’ and it’s original size is 2MB. Similarly, the
logical name of the transaction log is ‘sample_log’, and it’s original size is 1MB.
The physical data file is ‘sample.mdf’ and it is by default created in the folder ‘C:\Program Files\Microsoft
SQL Server\MSSQL.1\MSSQL\DATA’. The physical log file is ‘sample_log.ldf’ and it is by default created in
the folder ‘C:\Program Files\Microsoft SQL Server\MSSQL.1\MSSQL\DATA’.
creates a database named ‘projects’ with the given specifications for the data file. Uses default
specifications for the log file.
Logical names and folders could be specified thru the GUI method of creating the database, but physical
names coluld not be specified. But, thru the command method, you could even specify the physical names
also.
Constraints:
Usually created at the same time as the table creation.
Can also be added to a table after the table creation
Can also be temporarily disabled and enabled.
Can be permanently dropped
Constraints can be of Column-level(defined with the definition of the columns) or table-level(defined after
the definition of all the columns, i.e., not with the definition of the columns)
Not Null
NULL values not allowed
Duplicate allowed
Any number of NOT NULL in a table
It is a column level constraint
No composite NOT NULL exists
create table table2( empno numeric(5), empname varchar(10) not null default 'abc')
insert into table2 values(1,'tom');
insert into table2(empno) values(2);
Unique
Duplicates not allowed
NULL values allowed.
Composite Unique key allowed
However, no two rows can have NULL values. This applies to both individual, as well as, composite unique
keys.
create table table1( empno numeric(5) unique, empname varchar(10) not null default 'abc')
or
create table table1( empno numeric(5) constraint mycon1 unique, empname varchar(10) not null default
'abc')
In both the cases, it creates a constraint with a system-specified name. In 1 st case also creates a
unique,non-clustered index with a system-specified name. In the 2nd case creates unique,non-clustered
index with the name mycon1.
create table student(std numeric(1), div char(1), rollno numeric(2), studname varchar(10), unique(std,div,
rollno))
To create a composite Unique key. Here, it does not create a constraint as an object as such, but creates a
unique,non-clustered index with a system-specified name
Or
create table student(std numeric(1), div char(1), rollno numeric(2), studname varchar(10), constraint sdr
unique(std,div, rollno))
To create a composite Unique key. Here, it does not create a constraint as an object as such, but creates a
unique,non-clustered index with the name sdr.
create table table1(c1 numeric, c2 char(10))
If size is not specofied for numeric column, it takes the maximum size as (18,0).
To disable a constraint :
alter table table1 nocheck constraint abc
To re-enable a constraint :
alter table table1 check constraint abc
create table table4(empno numeric(3) constraint mycons unique not null, empname varchar(10))
Here, for the unique key, no constraint is created as such, but a unique, nonclustered index with the
specified name is created.
Create table table5(empno numeric(3) constraint mycon2 unique clustered, empname char(10))
Here, for the unique key, no constraint is created as such, but a unique, clustered index with the specified
name is created.
or
Create table table5(empno numeric(3) constraint mycon2 unique clustered not null , empname char(10))
By default, a unique key constraint creates a non-clustered index on the specified column(s). To create a
clustered inndex, it is needed to specify the keyword clustered.
Primary Key
Key that uniquely identifies each row of a table
Duplicate values not allowed
Null values not allowed
Recommended for every table
Can have a Composite PK
Null values not allowed for any column of the Composite PK.
Only one PK/Composite PK per table
PK can be defined at column level. CPK is always defined at table-level.
Create table emp(empno numeric(3) constraint xyz primary key nonclustered, empname varchar(20))
Here, primary key constraint is created on column empno, but as the option nonclustered is specified, the
index xyz which is created will be of type unique,nonclustered.
Create table stud(std numeric(2), div char(1), rollno numeric(3), studname varchar(25), primary
key(std,div,rollno))
Or
Create table stud(std numeric(2), div char(1), rollno numeric(3), studname varchar(25), constraint abcd
primary key(std,div,rollno))
To create a composite primary key on the specified columns. In the 1 st case the index is created with a
system-specified name, and in the 2nd case the index is created with the specified name. In both the cases,
the index is of type unique,clustered.
Or
Create table stud(std numeric(2), div char(1), rollno numeric(3), studname varchar(25), primary key
nonclustered(std,div,rollno))
To create a composite primary key on the specified columns which will create a unique, nonclustered index
with a system-specified name.
Create table stud(std numeric(2), div char(1), rollno numeric(3), studname varchar(25))
alter table stud add primary key(std,div,rollno)
Error : Cannot define PRIMARY KEY constraint on nullable column in table 'stud'.
Foreign Key
create table dept(deptno numeric(3) primary key, deptname varchar(10))
create table emp(empno numeric(5), empname varchar(20), deptno numeric(3) references dept(deptno))
Foreign key refering to another column of another table where the referenced column is Primary key
create table dept(deptno numeric(3) unique, deptname varchar(10))
create table emp(empno numeric(5), empname varchar(20), deptno numeric(3) references dept(deptno))
Foreign key refering to another column of another table where the referenced column is Unique key
The coulmn to which the foreign key column refers must be Primary key or Unique key.
create table emp(empno numeric(3) primary key, empname varchar(10), mgrno numeric(3) references
emp(empno))
Foreign key refering to another column of the same table where the referenced column is Primary key or
Unique key
create table emp(empno numeric(5) not null, empname varchar(20), deptno numeric(3))
alter table emp add foreign key(deptno) references dept(deptno), primary key(empno)
Foreign key created after table creation through the alter table command. Also, addition of more than one
constraint through a single alter command is allowed
create table table1(c1 char(3), c2 numeric(3), c3 char(3), c4 numeric(3), unique(c1,c2), foreign key(c3,c4)
references table1(c1,c2))
Composite forein key
create table table1(c1 char(2), c2 numeric(3), c3 char(3), c4 numeric(3), unique(c1,c2), foreign key(c3,c4)
references table1(c1,c2))
create table table1(c1 numeric(3), c2 numeric(3), c3 numeric(3), c4 numeric(4), unique(c1,c2), foreign
key(c3,c4) references table1(c1,c2))
create table table1(c1 numeric(3), c2 numeric(3), c3 numeric(3), c4 char(3), unique(c1,c2), foreign
key(c3,c4) references table1(c1,c2))
error : since the dataytype, as well as, datasize of the first referencing coulmn must be the same as that of
the first referenced column and the dataytype, as well as, datasize of the second referencing coulmn must
be the same as that of the second referenced column
create table emp(empno numeric(3) primary key, empname varchar(10), deptno numeric(3) references
dept(deptno) on update no action on delete no action)
It is as good as telling SQL Server not to take any alternative course of action and hence just do not allow to
update or delete records from the parent table who have 1 or more child records.
create table emp(empno numeric(3) primary key, empname varchar(10), deptno numeric(3) default 1
references dept(deptno) on delete set default on update set default )
Foreign key values are set to the default value 1 when either the corresponding referenced column is
updated or the corresponding parent record is deleted. But, there must be a record in the parent table with
deptno=1, or else the parent updations and deletions will fail.
CHECK
create table table1(c1 numeric(3) check (c1 in(1,2,3)), c2 char check (c2 ='a'))
Column c1 will allow only (1,2,3) as legitimate values, and column c2 will only allow ‘a’ as a value. But,
NULL values are allowed in both cases, unless otherwise also specified as NOT NULL as follows :
create table table1(c1 numeric(3) not null check (c1 in(1,2,3)), c2 char not null check (c2 ='a'))
RETRIEVAL :
--The Where clause is used to define one or more conditions to limit the retrieval of only those rows that
satisfy the given criteria. The net result of the where clause ia a TRUE or FALSE that is tested for each row
to be returned. If TRUE then the row is returned, if FALSE, the rows is not returned.
select * from emp where empno>=3
select * from emp where empname='jairaj'
Select * from emp where empno=25 and empname='jairaj' or empname='saloni' and deptno=1
--Here the system evaluates both the AND operators first(from left to right), and then the OR operator is
evaluated
Select * from emp where ((empno=25 and empname='jairaj') or empname='saloni') and deptno=1
--Use of parenthesis changes the entire operation execution with all the expressions within parenthesis
being executed first in the sequence from left to right. The use of parenthesis is highly recommended, even
though it is not compulsory. It also improves readibility of the SELECT statement and possible errors are
also avoided.
IN Operator
The IN operator can be used instead of a series of conditions separated by OR on a single column.
Select * from emp where empno IN (100,105,110)
To find out rows that are not equal to any of the listed values, use the NOT IN operator
Select * from emp where empno NOT IN (100,105,110)
BETWEEN Operator
To specify a range which determines the lower and upper bounds of qualifying values.
Select * from emp where sal BETWEEN 10000 and 20000
The Between operator searches for all the values in the range inclusively.
To find out the rows where the specified column does not fall within the specified range, use the NOT
BETWEEN operator
Select * from emp where sal NOT BETWEEN 10000 and 20000
IS NULL
NULL values cannot be directly compared using the comparison operator =. Comparison with NULL using =
operator will evaluate to false and return no rows. Comparison with NULL is done with the operator IS NULL
Select * from emp where deptno is null
To find rows that have got non-null values for a specific column, make use of IS NOT NULL
Select * from emp where deptno is not null
Or
Select * from emp where not deptno is null
LIKE operator
LIKE Operator is used for searching strings that follow a particular pattern. There are two patern matching
Operators
% represents 0 to n characters. _ represents only 1 character
select * from student where sname like 'd%'
select * from student where sname like '__m%'
select * from student where sname like '__m'
select * from student where sname like '__m__'
The Count() function returns a value of type INTEGER. Hence, if the return value exceeds the range of
INTEGER type, then make use of COUNT_BIG() function which returns a value of type BIGINT.
When group functions are used without group by clause, the entire table(or records of the table which satisfy
the given condition(s)) are considered as a single set for calculating the aggregate/summarised value as per
the function given
select t.tname, max(s.age), min(s.age), avg(s.age), sum(s.age) from teacher t full outer join student s on
t.tcode=s.tcode group by t.tname
Group by can also be done in a join of two or more table. A group is also formed for students without a
teacher. And groups are also formed for each such teacher including teachers who do not have students
Grouping can also be done on the basis of more than one columns as follows
Select std, div, max(maths), avg(english) from students group by std, div
Conditions can be given with a HAVING clause to further filter the output of the GROUP By clause. Thus,
having clause gives us filtered summarised data, and comes into picture only after the group By clause
select rollno, sum(maths) from studmarks group by rollno having sum(maths)>100 and sum(maths)<300 and
avg(maths)>60
select std, sum(maths) from studmarks group by std having sum(maths)>100 and sum(maths)<300 and
avg(maths)>60 order by std desc
select std, sum(maths) from studmarks group by std having sum(maths)>100 and sum(maths)<300 and
avg(maths)>60 order by sum(maths) desc
Order by clause can be used as the last clause, if required
select sch, std, div, max(maths) from students group by sc, std, div with Rollup
Apart from the sum of marks for each DIV within each STD within each SCH(like the normal GROUP BY), it
will also show us the sum of marks for each STD within SCH, sum of marks for each SCH, and the Grand
sum for all the students.
Thus, ROLLUP does additional grouping considering the last column(nth column) as one column and the
remaining columns(1 to n-1 columns) as a single column
select sc, std, div, max(maths) from students group by sc, std, div with Cube
Apart from the sum of marks for each DIV within each STD within each SCH(like the normal GROUP BY), it
will also show us the sum of marks for each STD within SCH, sum of marks for each DIV within a SCH, sum
of marks for each DIV within a STD, sum of marks for each SCH, sum of marks for each STD, sum of marks
for each DIV and the Grand sum for all the students.
Thus, CUBE does additional grouping on all the combinations of the n columns involved
ORDER BY clause
To arrange the retrieved rows in the order of a particular column. The column in the order by clause need
not appear in the SELECT list. By default it arranges the rows in the ASCENDING order, hence specifying
ASC is optional. For descending the keyword is DESC. More than one column can be included in the
ORDER BY clause. DESC/ASC need to be mentioned separately for each column in the order by clause
Select top 1 deptno, avg(sal) from emp group by deptno order by 2 desc
It sometimes becomes becessary to modify the representation of data as per some predefined codification.
Such a requirement would normally require some sort of programming technique. Instead the CASE
expression makes this possible without any need for programming.
There are two forms of CASE :
1)Simple CASE expression
Synatx :
CASE Expression
When value1 then result1
When value2 then result2
When value3 then result3
When valuen then resultn
Else resultn+1
End
select empno, empname, case mgrno when 1 then 'Manager 1' when 2 then 'Manager 2' when 3 then
'Manager 3' when 4 then 'Manager 4' when 5 then 'Manager 5' else 'No Manager' end from employee
Here, the entire CASE expression has been given the alias ‘departmentname’
SUBQUERIES
It is the concept of query within a query. The main query is called OUTER query and the subquery is called
the INNER or NESTED query.
2) Correlated
Here, for each row of the outer query the inner query is evaluated again and again. Thus, the inner
query is evaluated more than once.
Simple Subqueries
select * from emp where deptno=(select deptno from emp where empname='hemant')
To display all the rows where deptno is the same as that of ‘hemant’. Here we are assuming that there is
only person with empname=’hemant’. If the inner query returns no rows or null value, then in both cases the
outer qury returns no rows.
Select * from stud where std=(select std from stud where rollno=101) and div=(select div from stud where
rollno=101)
Select * from students where maths>(select maths from students where studname='Laxman')
Select rollno, firstname from students where maths=(select max(maths) from students);
Select deptno, min(sal) from emp group by deptno having min(sal)>(select min(sal) from emp where
deptno=20);
Multirow-Subqueries
If the inner query returns more than one row than comparison operators like =,<,> fail and will cause an
error. For inner queries returning more than one row we can use multirow comparison operators : IN, ANY or
ALL
select * from emp where deptno in (select deptno from emp where empname='jairaj')
select * from emp where sal<any(select sal from emp where deptno=20) and deptno<>20
or
select * from emp a where exists(select sal from emp b where b.deptno=20 and a.sal <b.sal) and
deptno<>20
or
select * from emp where sal<some(select sal from emp where deptno=20) and deptno<>20
SOME is the synonym for ANY
select * from emp where sal=any(select sal from emp where deptno=20) and (deptno<>20 )
select * from emp where sal<all(select sal from emp where deptno=20) and deptno<>20
Assume there are 2 tables : Employees(containing employee’s details) and Projects(containg one record for
each project that an employee works on and an employee may work on more than one project)
Suppose Tom goes on long leave and hence is currently not working on any projects. Hence projid in
Projects table needs to be set to null for all records where empid is Tom’s empid
Update projects set projid=null where empid in (select empno from employees where ename=’Tom’)
Assuming there is only 1 tom, hence in place of IN you could even use =
Assume there are 2 tables : Employees(containing employee’s details) and Projects(containg one record for
each project that an employee works on and an employee may work on more than one project)
Suppose Tom resigns hence is not working on any projects. Hence, all rows in projects on which tom was
working need to be deleted.
Delete from projects where empid in (select empno from employees where ename=’Tom’)
Assuming there is only 1 tom, hence in place of IN you could even use =
Assume there are 2 tables : Employees(containing employee’s details) and Projects(containg one record for
each project that an employee works on and an employee may work on more than one project)
Correlated Subqueries :
Unlike a normal nest query, in a correlated sub query, the inner query is driven by the outer query. Each
time a row from the outer query is process, the inner query is evaluated
Select * from emp e where e.sal>(select avg(sal) from emp d where d.deptno=e.deptno)
Here for every row of e, the salary of employees is compared with the average salary from d calculated
department wise
To find out all the employees who work on the project ‘P3’
Select * from employees where empid in (select empno from projects where projno=’P3’)
Normal Query
Or
Select * from employees where ‘P3’ in (Select projno from projects where project.empno=emplyees.empid)
Correlated subquery
To find out all employees who have at least one employee reporting to them
Select empid, empname, deptno from employee e where EXISTS( Select 'X' from employee where
mgrid=e.empid)
Select empid, empname, deptno from employee e where NOT EXISTS( Select 'X' from employee where
mgrid=e.empid)
Correlated Update
Alter table emp add deptname varchar(10);
Correlated DELETE
To delete rows from outer table based on rows of the inner table.
Suppose there are two tables : Employees and Employees_History. The Employees table contains details of
all current employees and Employees_History table contains rows of retired employees. Let us assume a
situation where due to some reasons some retired employees’s records are also present in the current
employees table and you have to delete all such records.
To find all the orders whose prices are greater than the average of all prices for the year 2005, and whose
freight is greater than 1/10th of the average of all prices for the year 2005
Select * from freights where price>(select avg(price) from freights where year(orderdate)=’2005’) and
freight>(select avg(price) from freights where year(orderdate)=’2005’)/10
The above query contains two subqueries which are almost identical and hence the entire query becomes a
bit too lengthy. Also, the query-columns are calculated for each of it’s execution. One way to shorten the
query would have been to create a view conatining the inner query and then use it where-ever required. But
then we would have to create the view and then drop it after it’s use.
Instead we can write a Common Table Expression(CTE) using the WITH clause. The Non-recrursive form
of CTE can be used as an alternative to derived tables(Derived table is a table expression defined in the
FROM clause of a SELECT statement that exists for the duration of the query)
Syntax :
WITH cte_name(column_list) AS
(inner_query)
Outer_query
WITH price_calc(avg2005) as
(Select avg(price) from freights where year(orderdate)='2005')
Select * from freights where price>(select avg2005 from price_calc) and freight>(select avg2005 from
price_calc)/10
Thus we don’t have to create views and then drop it. Rather, the inner query definnes the Select statement
which specifies the result set of the CTE and then we can use the CTE in the outer query
WITH price_calc(avg2005) as
(Select avg(price) from freights where year(orderdate)='2005'),
Freight_calc(freight2005) as
(Select avg2005/10 from price_calc)
Select * from freights where price>(select avg2005 from price_calc) and freight>(select freight2005 from
freight_calc)
Here we have created one CTE from another CTE, which is also allowed
Union clause between 2 queries shows common records retrieved by the two queries once and uncommon
records once.
select * from employee1
union
select * from employee2
When records of the two tables are exactly the same that is exactly same values for all the columns and
exactly same number of rows, then the output will be exactly the same as one of the select commands
involved.
Make changes to the values of empname column in certain records of both the tables and then retry the
command to notice the difference. Then make changes to different columns of the two tables and then retry
the command again.
select * from employee1
union
select * from employee2
Union ALL clause between 2 queries shows common records as many number of times as the number of
queries involved and uncommon records once.
select * from employee1
union all
select * from employee2
Intersect clause between 2 or more queries shows only the common records once, and does not display
uncommon records at all
select * from employee1
intersect
select * from employee2
Except clause between 2 queries shows records of the first query which are not present in the second query
select * from employee1
except
select * from employee2
IDENTITY column
To select a column of type IDENTITY, you need not specify it's name, but can use the keyword
IDENTITYCOL in the SELECT statement
select identitycol from itemmast1
When the data type of a column is of type IDENTITY, values cannot be specified for such a column as the
values are autogenerated. If, however, you want to supply your own values for certain rows, then before
inserting the rows thru the insert command , the IDENTITY_INSERT option must be set to on using the
following statement
set identity_insert itemmast1 on;
Also, when inserting values manually, you need to specify the column names in the braces after the table
name or else it will give you an error, since specifying values for columns of type identity requires that the
column name be explicitly mentioned.
That is
insert into itemmast1 values(118,'Floop', 12);
will give an error though it is syntactically right
IDENTITY column will now start generating values considering the current largest value in the table and not
from where it left.
COMPUTE clause
It uses aggregate functions (min, max, sum, avg) to calculate sumarrised values that appaer as additional
rows in the result of the query. The result of the compute clause is not a table, but a report. Hence, the
compute clause does not belong to the Relational Model, which forms the basis of all RDBMS packages.
Compute clause has an optional BY option. BY defines the grouping form of the result. The option By
coumn_name is like the group by column_name. However, the ORDER BY is compulsory if COMPUTE BY
is used
select * from emp order by deptno, empname compute min(sal), max(sal) by deptno, empname
Temporary Tables
There are two types of temporary tables: local and global. Local temporary tables are visible only to their
creators during the same connection to an instance of SQL Server as when the tables were first created or
referenced. Local temporary tables are deleted after the user disconnects from the instance of SQL Server.
Global temporary tables are visible to any user and any connection after they are created, and are deleted
when all users that are referencing the table disconnect from the instance of SQL Server.
Create both the below mentioned tables and insert records into them thru the same connection
use projects
create table #emp1(empno numeric(3), empname varchar(10))
Now, Click on File, New, Query with Current Connection/or click on the New Query button on the Standard
Toolbar
Now in this session
select * from #emp1
will fail
But
select * from ##emp1
will succeed
Again, Now, Click on File, New, Query with Current Connection to start one more new session
Now in this session
select * from #emp1
will fail
But
select * from ##emp1
will succeed
Now close all the Query Sessions, including the session in which the two temporary tables(lolcal and global
temporary tables were crreated), and then try the following :
select * from #emp1
will fail
But
select * from ##emp1
will fail
Computed Columns
Computed columns are by default virtual columns that are not physically stored in the table. Their values are
recalculated each time they are referenced in a query.
While inserting records do not specify values for the computed columns
insert into orders values(1,getdate(),5,10)
select getdate()+7
insert into orders values(1,getdate(),6,15,90,getdate()+7)
This will give an error saying : Column name or number of supplied values does not match table definition.
With SQL 2005, the keyword PERSISTED can be used in the Create table or Alter table so that the
computed column is physically stored in the table. Also index can be created for a persisted computed
column.
Columns on the basis of which computed columns are build must belong to the same table. Default cannot
be applied to computed columns
Subqueries are advantageous over joins when you have to calculate an aggregate value on the fly and use
it in the outer query for comparison
Eg:
Select * from students where maths=(Select max(maths) from students)
Joins are advantageous over subqueries when the SELECT list contains columns from more than one table.
Eg:
Select employee.empno, employee.empname, works.job from employee, works where
employee.empno=works.empno
Here you cannot use a subquery since the subquery can only display columns from the outer table
JOINS
To join two or more table, you can use two different syntax forms :
[INNER] JOIN
LEFT [OUTER] JOIN
RIGHTT [OUTER] JOIN
FULL [OUTER] JOIN
CROSS JOIN
ANSI
Select * from emp INNER Join dept on emp.deptno=dept.deptno
Select * from emp INNER Join dept on dept.deptno=emp.deptno
Positioning of columns in the ON cluase is not significant. In both cases columns of emp table are shown
and then the columns of dept table are shown. The * indicates all the columns from both the table involved in
the join.
Select * from dept INNER Join emp on dept.deptno=emp.deptno
Select * from dept Join emp on emp.deptno=dept.deptno
The result of an EQUI/INNER join is records that have identical values for one or more pairs of columns.
There can be more than one pair of columns as follows :
Select emp.*, dept.* from dept Join emp on emp.deptno=dept.deptno and dept.dcity = emp.ecity
Here, assuming that dcity indicates the city of a particular department and ecity indicates the city of an
employee. Thus, the query would mean all the employees who stay in the same city as that of their
respective department.
SQL SERVER
Select * from emp,dept where emp.deptno=dept.deptno
Select * from emp,dept where dept.deptno=emp.deptno
Select * from dept, emp where dept.deptno=emp.deptno
Select emp.*, dept.* from dept, emp where dept.deptno=emp.deptno
select empname,sal, deptname from dept, emp where dept.deptno=emp.deptno
Select * from dept,emp where emp.deptno=dept.deptno and dept.location = emp.address
Here, the type of connection between the two tables is specified in the WHERE clause using one or more
pairs of columns.
The semantics of the corresponding join columns must be identical. That is both of them must have the
same logical meaning. It is not necessary that the corresponding join columns must have the same name.
The names of columns in the SELECT list or any other part of the query which involves columsn can be
QUALIFIED to avoid any possible ambiguity which will occur if the tables have columns with identical
names. A column name is QUALIFIED as TABLENAME.COLUMNNAME or
TABLEALIASNAME.COLUMNNAME
In an EQUI/INNER join, the following possible strategy is used to give you the output :
First of all, each row of EMP table is joined with each row of DEPT table. The result of this will be a table
with all the columns from both the tables and n X m rows, where n=number of rows from EMP and m=
number of rows from DEPT.
Secondly, all the rows from the above nXm rows which satisfy the join condition
EMP.DEPTNO=DEPT.DEPTNO are displayed.
ANSI
Select * from emp CROSS JOIN dept
SQL Server
Select * from emp, dept
If the WHERE cluase contains something other than the JOIN condition, the result is still a Cartesian
Product, but will show only those rows that satisfy the condition in the where clause :
1 HH 1100
2 JJ 2100
3 KK 20000
4 LL 21000
5 OO 26000
6 II 30000
7 UU 35000
8 YY 39999
9 TT 40000
10 RR 45000
11 QQ NULL
12 BB 750
A 1000 10000
B 10001 20000
C 20001 30000
D 30001 40000
ANSI
Select e.empno, e.ename, e.salary, j.grade from employee e join Sal_Grade j on e.salary BETWEEN
j.Min_Sal and j.Max_sal
SQL Server
Select e.empno, e.ename, e.salary, j.grade from employee e, Sal_Grade j where e.salary BETWEEN
j.Min_Sal and j.Max_sal
Here, all the employees are shown except 10,11,12 as they do not fall in any of the grades mentioned in the
table sal_grade
Suppsoe you want to know all the employee information and department information such that the address
of the employee alphabetically preceeds the location
ANSI
Select distinct empno from emp join dept on address<location order by empno
SQL Server
Select distinct empno from emp, dept where address<location order by empno
Here, if you don’t put distinct or include any other column you will get a cartesian product
SQL Server
Select emp.*, dept.* from emp, dept where emp.deptno=dept.deptno and address<location order by empno
NATURAL JOIN
In SQL Server, the meaning of Natural join is that the SELECT list should not have repetitive columns, which
happens in an Equi/Inner join which is performed on the basis of one or more pairs of columns which may
have identical values for the pair(s) of columns involved in the join.
ANSI
SELECT s.*, st.english, st.maths, st.science FROM STUDENT s join STudentmarks st on s.rollno=st.rollno
and s.std=st.std and s.div=st.div
SQL SERVER
SELECT s.*, st.english, st.maths, st.science FROM STUDENT s, STudentmarks st where s.rollno=st.rollno
and s.std=st.std and s.div=st.div
The SELECT List of a natural join need not contain all non-identical columns, but it simply does not include
the redundant join columns
ANSI
SELECT s.name, st.english FROM STUDENT s join STudentmarks st on s.rollno=st.rollno and s.std=st.std
and s.div=st.div
SQL SERVER
SELECT s.name, st.english FROM STUDENT s, STudentmarks st where s.rollno=st.rollno and s.std=st.std
and s.div=st.div
Here the pairs of columns on the basis of which the join is performed are not unnecessarily repeated in the
SELECT list
SELF JOIN
Here, a table is joined to itself, whereby a single column of a table is compared to itself or one column of the
table is compared with another column of that very table. For this it becomes necessary to treat that single
table as two different tables and then considering them as two separate table perform the join between the
pair or pairs of columns. This can be accomplished by giving aliases to the table so that it can appear twice
in the FROM clause
ANSI
select t1.deptno, t1.deptname, t1.location from dept t1 join dept t2 on t1.location=t2.location and
t1.deptno<>t2.deptno
SQL SERVER
select t1.deptno, t1.deptname, t1.location from dept t1 , dept t2 where t1.location=t2.location and
t1.deptno<>t2.deptno
select ep.empname as BOSS, ec.empname as WORKER from employee1 ep, employee1 ec where
ec.mgrid=ep.empid
OUTER JOINS
In case of EQUI/INNER, THETA, NATURAL, SELF joins, the result always included rows from one table that
have corresponding rows in the other table. Thus only MATCHING rows from both sides are shown.
Sometimes it is necessary to show UNMATCHED rows in addition to the MATCHED rows. This is achieved
through OUTER Joins
SQL SERVER
Select * from dept, emp where emp.deptno*=dept.deptno
The use of ‘*=’ and ‘=*’ are not compatible or disappreciated feature in SQL 2005. Hence make use of ANSI
standards only
SQL SERVER
Select * from dept, emp where emp.deptno=*dept.deptno
SQL Server
Select * from dept, emp where emp.deptno=*dept.deptno
union
Select * from dept, emp where emp.deptno*=dept.deptno
select t.tname, s.sname, sm.english, sm.maths, sm.science from teacher t join student s on t.tcode=s.tcode
join studmarks sm on s.rollno=sm.rollno
select * from teacher t left outer join student s on t.tcode=s.tcode left outer join studmarks sm on
s.rollno=sm.rollno
Output of the first LOJ is further LOJoined with the studmarks table
select * from teacher t left outer join student s on t.tcode=s.tcode right outer join studmarks sm on
s.rollno=sm.rollno
Output of the first LOJ is further ROJoined with the studmarks table
select * from teacher t right outer join student s on t.tcode=s.tcode right outer join studmarks sm on
s.rollno=sm.rollno
Output of the first ROJ is further ROJoined with the studmarks table
select * from teacher t right outer join student s on t.tcode=s.tcode left outer join studmarks sm on
s.rollno=sm.rollno
Output of the first ROJ is further LOJoined with the studmarks table
select * from teacher t full outer join student s on t.tcode=s.tcode full join studmarks sm on s.rollno=sm.rollno
Output of the first FOJ is further FOjoined with the studmarks table
select * from teacher t full outer join student s on t.tcode=s.tcode left join studmarks sm on s.rollno=sm.rollno
Output of the first FOJ is further LOjoined with the studmarks table
select * from teacher t full outer join student s on t.tcode=s.tcode Right join studmarks sm on
s.rollno=sm.rollno
Output of the first FOJ is further ROjoined with the studmarks table
Transact SQL
If condition(s)
begin
statement1
statement2
end
If condition(s)
statement1
or
If condition(s)
begin
statement1
statement2
end
else
begin
statement3
statement 4
end
In the if section or in the else scetion there is only one statement, then the Begin...... End is not required.
WHILE
The While statement repeatedly executes a statement or more than one statements(enclosed within a
begin… end) till the boolean expression evaluates to true. Thus, if the expression/condition is true, the
statement or block of statements is executed and then the expression/condition is checked again to
determine if the statement or block of statements should be executed again.
The block within the while statement can optionally contain one or more statements used to control the
execution of statements within the block : BREAK or CONTINUE. BREAK statement stops the execution of
the statements inside the block and starts execution of the statement immediately following this block.
CONTINUE statement stops only the current execution of statements in the block and starts the execution of
the block again
declare @a int, @b int
set @a=1
set @b=0
while(@a<=10)
begin
print @a
set @b=@b+@a
print @b
set @a=@a+1
end
To print numbers from 1 to 10 and their sum
declare @a int
set @a=0
while(@a<10)
begin
set @a=@a+1
if(@a=5)
continue
print @a
end
To print numbers from 1 to 10 except 5
GOTO can exist within conditional control-of-flow statements, statement blocks, or procedures, but it cannot
go to a label outside the batch. GOTO branching can go to a label defined before or after GOTO.
print @a
set @b=@b+@a
print @b
set @a=@a+1
end
Here, WAITFOR DELAY '00:00:30', specifies that the execution should be delayed by 30 seconds
while(@a<=10)
begin
WAITFOR delay '00:00:10'
print @a
set @b=@b+@a
print @b
set @a=@a+1
end
This will not print values with an interval of 10 seconds as the logic looks, but will do the printing work
together after 10X10=100 seconds
Expand “SQL Server Agent”, “Error Logs”. Double-click on “Current 2-11-2010” (this will display the Log File
Viewer window, which contains various types of error logs). Expand the error logs for “SQL Server”. Select
the check-box for “Current 2-11-2010”. On the right-side you will see the details of all the errors. Notice the
difference for 50002 and 50009 user-defined errors.
Raiseerror
Generates an error message and initiates error processing for the session.
Sp_addmessage is a system stored procedure that creates a user-defined error message with an error
number and severity level. Error number must be greater than 50000(Error numbers less than 50000 are
reserved for SQL Server System)
With sp_addmessage you specify the Error number, the Error message,Severity level, Language in which
the message is to be displayed, and @with_log is set to true so that user-defined error message is written to
the event log(as user-defined messages are by default not written to the log). @replace=’replace’ to
overwrite an existing user-defined message
Handling Events with TRY and CATCH Statements
SQL Server 2005 handles exceptions using the TRY and CATCH statements. An Exception is a problem or
an error that prevents the continuation of a program. With such a problem you cannot continue the program
processing. Hence, this problem will be directed to another part of the program wherein the problem will be
dealt with.
The TRY statement does the work of capturing the exception. Since any program consists of several
statements, we have a TRY block. When an error/exception occurs in the TRY block, the exception/error is
delivered to another part of the program which will handle the exception. This part of the program which will
handle the error/exception is denoted by the keyword CATCH and hence is called the CATCH block.
Consider an Example of DEPT table and EMP table, where deptno in EMP table is Foreign Key to Deptno
column in DEPT table.
Now consider the following Transaction which attempts to add 4 records to the Emp table :
Begin Transaction
insert into emp values(200,'a',30,500, 'xyz')
insert into emp values(201,'b',30,500, 'xyz')
insert into emp values(202,'c',33,500, 'xyz')
insert into emp values(203,'d',30,500, 'xyz')
Commit transaction
Suppose, 33 is not a valid deptno in the DEPT table. Then, the first two records are added and the 3rd
record will generate an error. But the processing of the block will continue and the 4 th record will also be
added.
Suppose, the situation is that either all 4 should be added or none of them should be added. This can be
handled using TRY and CATCH as follows :
Begin TRY
Begin Transaction
insert into emp values(300,'a',30,500, 'xyz')
insert into emp values(301,'b',30,500, 'xyz')
insert into emp values(302,'c',33,500, 'xyz')
insert into emp values(303,'d',30,500, 'xyz')
Commit transaction
print 'Transaction succeded'
End TRY
Begin CATCH
Rollback
Print 'Transaction failed..'
End CATCH
(1 row(s) affected)
Transaction failed..
Here, the first 2 Inserts are executed, and hence in the output you will see “1 row(s) affected” twice. Then
the third Insert fails. As all the 4 statements are written inside the TRY block, an exception is raised or
thrown and the exception handler starts the CATCH block. The CATCH block rollsback all the statements
and prints an appropriate message.
Stored Procedure
Procedure to display employees with deptno=30
Create procedure p1
As
Select * from emp where deptno=30
To execute Procedure P1
execute p1
Procedure to display employees with deptno=30 and then employees with deptno=20
Create procedure p2
As
Select * from emp where deptno=30
Select * from emp where deptno=20
To execute Procedure P2
exec p2
Procedure to display employees with deptno=30 and then employees with deptno=20 and then call
procedure p1
Create procedure p3
As
Select * from emp where deptno=30
Select * from emp where deptno=20
exec p1
To execute Procedure P3
exec p3
To drop procedure p1
drop proc p1
Now, if you execute Procedure p3, it will execute the first two lines and display an error for the third line as it
cannot find p1
Exec p3
It will still create p4, with an error message for the missing object p1 and will also allow you to execute it.
When executed it will again show an error message for the third line
This feature has a number of limitations and is marked by Microsoft as a depreciated feature, and hence will
be removed from future versions of MS SQL SERVER
alter procedure p2
As
Select * from emp where deptno=1
Drops the entire procedure p2 and creates it again with the above mentioned statement
To execute :
Exec pm1 10
Exec pm1 20
Exec pm1 30
As the procedure pm1 expects a value for the INPUT parameter @dept
exec incr_sal 10
exec incr_sal
Asuming that there is no PK-FK relationship between the two tables, such a procedure can be used as part
of the maintenance of referential constraint. Such a procedure can be used inside the defintion of a trigger,
which actually maintains the referential constraint.
Asuming that there is a PK-FK relationship between the two tables, then at execution time, the above
procedure will give two errors(one for each update) as both of them will separately attempt to viloate the FK
constraint, and hence both the statements will be terminated separatrly and no changes will be made to
either table
This procedure has 1 input and 1 output parameter. Th keyword OUTPUT has to be specified for a
parameter to become an output mode parameter. When the mode is not specified, it becomes an INPUT
mode parameter.
EXEC delt_dept
EXEC delt_dept 10
Both will generate errors, since procedure has got 2 parameters and needs to be executed with 2
parameters. However, since 2nd parameter is of type OUTPUT, the procedure will throw(output) a value to
the EXEC command. To catch this output(thrown) value, we need a variable which will catch the
thrown(output value) as follows :
The optional recompile option can be given in the Procedure definition. If the recompile option is given in the
procedure definition, it ignores the existing execution plan and generates a new plan each time the
procedure is executed. This destroys an important benefit of stored procedure being able to use an existing
execution plan, but sometimes it becomes necessary to regenerate a new plan with each new execution as
the database objects that are used/referred in the stored procedure change very frequently or when the
parameters passed to the stored procedure vary very widely with almost all the executions.
The recompile option can also be used with the execution of a procedure so that a new execution plan is
generated only for that execution of the procedure. In this case it is assumed that there is no recompile
inside the definition of the procedure, otherwise the entire idea of executing the procedure with recompile
option becomes meaningless. Execution with recompile is required when for that very execution the
parameters are going to vary very widely as compared to other previous executions
Suppose you want that either both should succeed or both should fail, you need to write them as a
transaction block and then either commit the transaction(that is commit both of them) or rollback the
transaction(rollback both of them)
Create procedure adddeptemp
@vdeptno numeric(3),
@vdeptname varchar(10),
@vempno numeric(3),
@vempname varchar(10),
@vsal numeric
as
begin transaction
insert into dept values(@vdeptno, @vdeptname)
If @@error <>0
Begin
print ' check the department'
Rollback tran
Return
End
The @@error system variable contains the error number of the latest transact sql statement. Hence, a value
of 0 means no error
print @@identity
commit transaction
SQL Server functions do not support output mode of parameters, but return a signle data value. The
RETURNS clause defines the Data-type of the value returned by the user-defined functions. This data type
can be any if the standard data types supported by SQL and the TABLE data type. TIMESTAMP/
TEXT/IMAGE data types cannot be returned. UDFs whose return-type is a Scalar SQL data type are called
scalar-valued functions, and UDFs whose return-type is TABLE are called table-valued
A UDF can be invoked in SQL statemsnt like SELECT, INSERT, UPDATE, DELETE. To invoke a UDF,
specify it’s name followed by parenthesis. Within the parenthesis, you can specify one or more arguments
that are passed to the INPUT parameters that are defined in the function header.
update emp set sal=dbo.myfunc(sal)
select dbo.calcsalr(10)
This function calculates the salaray of all the employees in the emp table and shows an amount which is X%
more than the total salary of all the employees. But, this function is limited to the table emp only.
-- Adding employees who report indirectly to those added in the previous iteration
WHILE @RowsAdded > 0
BEGIN
/*Mark all employee records whose direct reports are going to be
found in this iteration with processed=1.*/
UPDATE @reports
SET processed = 1
WHERE processed = 0
-- Insert employees who report to employees marked 1.
INSERT @reports
SELECT e.empno, e.empname, e.mgrno, 0
FROM employee e, @reports r
WHERE e.mgrno=r.empid and e.mgrno <> e.empno and r.processed = 1
SET @RowsAdded = @@rowcount
/*Mark all employee records whose direct reports have been found
in this iteration.*/
UPDATE @reports
SET processed = 2
WHERE processed = 1
END
If the RETURN clause specifies a variable as of table-type with list of columns, the function is called
MULTISTATEMENT Table-valued function. There is also an internal variable of type table which can be
used to insert rows into the table variable which is specified in the RETURN clause
Clustered and Non-Clustered Indices
SQL Server allows only one Clustered Index per table, since the clustered index determines the physical
order of the data in a table. It is built for each table implicitly where you define the Primary Key using the
Primary Key constraint. Also, a clustered index in SQL Server is Unique by default-that is each data value
can appear only once in a column for which the clustered index is defined. If a clustered index is built on a
non-unique column, the database system will enforce uniqueness by adding a 4-byte identifier to the rows
that have duplicate values.
Non-clustered indexes do not change the physical order of the rows in a table. At the leaf-level, a non-
clustered index consists of an index-key plus a bookmark. For each nonclustered index, SQL Server creates
an additional index structure that is tored in the Index. The bookmark on a nonclustered index shows where
to find the row corresponding to the index key. The bookmark part of the index key can have two forms :
when the table is a HEAP and when the table is CLUSTERED. Heap is a table without a clustered index. In
case of a Heap, the bookmark is identical to the Row Identifier(RID), which contains of two parts : the
address of the physical block where the corresponding row is tored and the poistion of the rows inside the
block. In case of a clustered index, the bookmark of the non-clustered index shows the b-tree structure of
the table’s clustered index.
In case of a Heap, the traversing of the nonclustered index structure will be followed by the retrieval of the
row using the row-identifier. In case of a Cluster, searching for data using a nonclustered index could be
twofold : the traversal of the nonclustered index structure will be followed by the traversal of the
corresponding clustered index. Thus a nonclustered index should be created only when you are sure that
there will significant performance gains.
An index can either be a single or a composite index. Single index has only one column, while a composite
index is built on more than one column and can contain maximum 16 columns
The UNIQUE option specfies that each data value can appear only once in the index column(s). If UNIQUE
is not specified , then duplicate values are allowed.
The CLUSTERED and NONCLUSTERED(default) option specifies a clustered and nonclustered index
respectively. Maximum of 249 nonclustered indexes allowed per table.
The INCLUDE option allows you to specify the nonkey columns(colums not mentioned in that particular
index) to be added to the existing columns of the nonclustered index. This can enhance performance as the
query-optimizer can locate all of the required data-values within the index and does not have to visit data-
pages. This is called “COVERED INDEX”.
The FIILFACTOR=n specifies the storage percentage for each index page, where n =1, ….., 100. If n=100,
each leaf index page will be 100 percent filled, and hence the existing index pages will have no space for
insertion of new rows. Hence FILLFACTOR=100 is only recommended for static tables. If Fillfactor is set to
a value between 1 and 99, it causes creation of a new index structure with leaf pages that are not
completely full. The bigger the value of fillfactor, the smaller the space that is left free on an index page.
Example a fillfactor=60 means that 40 percent of each leaf index page is left free for future UPDATE and
INSERT statements. When a page is split, the data will be distributed 50-50 between the two new pages.
PAD_INDEX option specifies the place to leave open/free on each intermediate index page of the B-tree.
IGNORE_DUP_KEY option should be used only to avoid the termination of long transactions which may
insert duplicate data in the indexed column(s). With this option enabled, an insert statement which attempts
to insert rows that violates the uniqueness, SQL Server returns a warning and does not insert the rows that
attempt to add the duplicate value. It ignores that row and continues with the others.
Each non-clustered index in a clustered table contains in it’s leaf nodes the corresponding values of the
table’s clustered index. For this reason, all the nonclustered indices must be rebuilt when a table’s clustered
index is dropped. The DROP_EXISTING option allows you to enhance performance when re-creating a
clustered index on a table that also has nonclustered indices.
IF the ONLINE option is activated, you can continue to make updates to the underlying data and perform
queries against the data, while the index is being created or dropped or rebuilt. In early versions of SQL
Server, such index operations held an exclusive lock on the underlying data and the associated indices
prevented modifications or queries until the index operation was complete.
The STATISTICS_NORECOMPUTE option specifies that the statistics of the specified index should not be
automatically recomputed.
ALLOW_ROW_LOCKS and ALLOW_PAGE_LOCKS specifies that the system uses row locks and page
locks respectively when the option is set to on.
The ON file_group option specifies the file group in which the specified index must be created.
The ASC/DESC options after the column name specifies whether the index is created on the
ascending/descending order of the column’s values. An index defined on the ascending order of column is
generally not usefull when you are searching values in the reverse order
Creation of a unique index for a column or composite columns is not possible if the column or columns
already contain duplicate values. Also, after the creation of a unique index any attempt to insert or modify
existing data which will create a non-unique value is also rejected by the system
Rebuilding an index drops and re-creates the index. This removes fragmentation, reclaims disk space by
compacting the pages based on the specified or existing fill factor setting, and reorders the index rows in
contiguous pages. When ALL is specified, all indexes on the table are dropped and rebuilt in a single
transaction.
Reorganizing an index uses minimal system resources. It defragments the leaf level of clustered and
nonclustered indexes on tables and views by physically reordering the leaf-level pages to match the logical,
left to right, order of the leaf nodes. Reorganizing also compacts the index pages. Compaction is based on
the existing fill factor value.
Disabling an index prevents user access to the index, and for clustered indexes, to the underlying table data.
The index definition remains in the system catalog. Disabling a nonclustered index or clustered index on a
view physically deletes the index data. Disabling a clustered index prevents access to the data, but the data
remains unmaintained in the B-tree until the index is dropped or rebuilt. Use the ALTER INDEX REBUILD
statement or the CREATE INDEX WITH DROP_EXISTING statement to enable the index.
There should be a UNIQUE index for each Primary key and each Candidate key of a table. Each column in
a Primary/Candidate key should have the NOT NULL constraint. You do not have to worry about Primary
key, as a unique index is automatically created for the Primary key and all the columns in a Primary key are
of type Not Null. Each foreign key should have a nonunique index as this significantly reduces execution
time needed for the corresponding join operations
Indexes created by the CREATE INDEX command are of type non-unique and non-clustered by default
In the 2nd case, for each employee the inner qury will be evaluated again and again. This happens as the
inner query in it’s where clause refers to emp.empno column which belongs to the table emp which is in the
FROM cluase of the outer query.
The join in the 1st case is much faster as it evaluates all the values of the column project.projno only once.
Views
Views do not exist physically. Their content is not stored on the disk. Views are database objects that are
always derived from one or more base tables. The name of the view and the way the rows from the base
tables are retrieved is the only information about the view that is physically stored. Thus, views are virtual
tables.
The SELECT statement in a view cannot include ORDER BY, INTO or COMPUTE clauses. Also, temporary
tables cannot be referred in the query of the view.
Simple views:
Derives data from a single table. Dose not contain functions or groups of data. Allows you to perform DML
operations.
create view v1 as select * from emp
select * from v1
Hence
set identity_insert dbo.emp on
insert into v1(empno, empname,deptno,sal,address) values(5010,'r',500,8000, 'A')
select * from v2
select * from v2
This row wont be retrievable through the view after this update command
Row which are not retrievable through the view cannot be updated.
Assume that both empno=810 and 1110 are having salaries less than 8000 and hence not available through
the view.
Views can have different column-names from the columns in the base tables
create view V3(employee_no, employee_name) as select empno, empname from emp
Simple views support DML operations subject to non-violation of constraints at the base table
create view v9 as select * from emp where deptno=500 and salary>=8000 with check option
insert into v9(empno, empname, deptno, salary, address, spousename, abc) values(9010, 'Tom', 500, 9000,
'Andheri', 'Pamela', 30)
Allowed
insert into v9(empno, empnames, deptno, salary, addresss, spousenames, abc) values(9020, 'Tom', 500,
7000, 'Andheri', 'Pamela', 30)
insert into v9(empno, empnames, deptno, salary, addresss, spousenames, abc) values(9020, 'Tom', 510,
17000, 'Andheri', 'Pamela', 30)
insert into v9(empno, empnames, deptno, salary, addresss, spousenames, abc) values(9020, 'Tom', 510,
7000, 'Andheri', 'Pamela', 30)
None of the above 3 inserts are allowed, as they violate the conditions given with the WHERE clause given
with the definition of the view. Same logic applies to UPDATE
WITH CHECK OPTION ensures that only those insertions/updations will be allowed through the view such
that the inserted/updated rows can later be retrieved through the view
create view v999 as select empno, e.deptno, empnames, salary from emp e join dept d on
e.deptno=d.deptno
create view v999 as select empno, deptno, empnames, salary from emp e join dept d on e.deptno=d.deptno
This will not create the view and will give an error as : Ambiguous column name 'deptno'
create view v999 as select empno, d.deptno, empnames, salary from emp e join dept d on
e.deptno=d.deptno
The view is created, but it will not support :
insert into v999(empno,d.deptno, empnames, salary) values(7070, 500,'Pat', 9000)
Insert will fail, as the insert affects multiple base tables
Complex views :
Derives data from many tables. Contains functions or groups of data. Does not allow DML operations
create view v5 as select deptno, sum(sal) sumsal from emp group by deptno
insert into v5 values(500, 9000)
Will give an error as V6 contains a derived or constant field.
To Drop a view
Drop View v1
When a table is dropped, the views that are based on that table are not dropped, but all such views become
inaccessible
create view v22 with schemabinding as select empno, empname, sal from emp
Error since when schemabinding is used the referenced table, views and functions must have two part
names as schemaname.object name as follows :
create view v22 with schemabinding as select empno, empname, sal from dbo.emp
An attempt to modify the structure of the referenced table, will give you warning messages saying that the
schemabinding of v22 will be removed. If you want to continue you may still go on and save the structural
changes you have made to it. Addition of new columns, modifications to columns which are not in the
SELECT list do not affect the schema-binding
INDEXED VIEWS
Views contain a query that acts as a filter. The SQL Server dynamically builds the result set from a query
that refers to a view. Dynamically means that the view always shows the updated content of the underlying
table. Building the result set dynamically can decrease performance, especially if the view with it’s select
statement proceseses many rows from one or more table. Also, if the view contains computations based on
one or more columns, the computations are performed each time you access the view, as the result set of a
view is build dynamically. If such view are frequently accesses in other queries, then you could significantly
increase performance by creating an index on the view.
Advantages
SQL Server allows to create indices on views and such views are called INDEXED or MATERIALISED
Views. When you create a unique clustered indexed view, the result set of the view(at the time the index is
created) is stored on the disk. Hence, all data modifications in the base table(s) will also be automatically
modified in the corresponding result set of the indexed view. After the creation of the unique clustered index
on the view, you may create any number of non-clustered indices on that view.
The most important advantage is that if a query does not explicitly refer to the indexed view, but contains a
column in the base table(s) which also exists in the index view, the SQL Optimizer estimates that using the
indexed view is the best choice and it chooes the view’s indices to solve that query
Queris that process many rows and contain join operations or aggregate functiions can gain performance
benefits if an indexed view is referred by the corresponding queries.
Triggers
A Trigger is a collection of SQL statements that looks and acts like a stored procedure, but a trigger cannot
be called with the EXEC command. Triggers are activated or fired when a user tries to Insert, Update or
Delete data.
Triggers is a tool that is invoked when a particular action occurs on a particular table. The action of a trigger
can be on a INSERT, UPDATE or DELETE statement. SQL Server 2005 also allows you to define triggers
on DDL statements
INSERT TRIGGER
They can be used to modify or even disallow a record being inserted.. Example : Insert Trigger could be
used to prevent users from entering records with salary less than 10000. Another use could be adding data
to the record being inserted, like adding the date when the record was inserted or adding the name of the
user inserting the record. It could even be used to cascade changes to some other tables in the database.
INSERT Triggers fire off(are executed) every time someone tries to create a new record in a table using the
INSERT Command. When a user tries to insert a new record into a table , SQL Server copies the new
record into the TRIGGER table(table in which user is attempting to add the new record) and also copies the
new record to a special table stored in the memory called the INSERTED table. Thus the new record being
inserted, exists in two tables : the TRIGGER table and the INSERTED table.
Example :
DELETE TRIGGER
They can be used to restrict the data that your users want to remove from a table. Example.: You may not
want your users to be able to remove records who belong to department=10 from the employees table. Or
you may also want to let your users delete records, but you want to update your management about the
records being deleted, the user who deleted the records and the time of deletion.
Ordinarily when a record is deleted, SQL Server removes that record from the table and the record is lost
permanently. With a DELETE trigger in place for a table, SQL Server moves the record being deleted to a
logical table called the DELETED table in the memory. Thus the record can still be referenced in your code
NOTE(DELETED, INSERTED tables are automatically purged of records after a transaction is complete, as
they are logical temporary tables in the memory)
UPDATE TRIGGERS
They are used to restrict UPDATE statements being issued by the users. Specifically designed to restrict the
existing data that your users can modify. Or may be allow the updations, but report the same to the
management or even update some other tables.
Update Triggers use both the temporary tables : INSERTED and DELETED. This is because an UPDATE
action is actually two separate actions : a delete followed by an insert. First the existing data is deleted and
then the new data is inserted. Thus the old record goes to the DELETED table and the new data goes to the
INSERTED table.
The 3 types of triggers can be combined. You can have an INSERT, UPDATE trigger or INSERT, DELETE
trigger or UPDATE, DELETE trigger or all three together.
RECURSIVE TRIGGERS
Those triggers that update other tables can cause triggers on those tables to fire. Such triggers are called
RECURSIVE triggers. In MS SQL Server, recursive triggers are disabled by default. In case you want to
enable it, right click on the database, select properties, and in the options tab, check the box next to
“RECURSIVE TRIGGERS”/ or set it to TRUE
else
begin
if (select inserted.science from inserted, students where
students.rollno=inserted.rollno)>100
begin
print 'science marks cannot be greater than 100'
rollback
end
else
begin
print 'maths or science have been updated'
update students set
students.total=students.maths+students.science+students.English from inserted where
students.rollno=inserted.rollno
end
end
end
The AFTER and INSTEAD OF are two additional options which you can define for a trigger. FOR is the
synonym for AFTER. AFTER triggers fire after the triggering event occurs. INSTEAD OF triggers are
executed instead of the corresponding triggering event. AFTER triggers can be created only on tables.
INSTEAD OF triggers can be created on both tables and views.
Multiple triggers can be created for each table and for each modification action
(INSERT, UPDATE, DELETE. ) By default there is no specific order in which multiple triggers for a particular
modification action.
When creating a triggered action, you may require to use the values of columns before or after the effect of
the triggering statement. For this, two virtual tables are used. The structure of thes tables is equivalent to
the structure of the table for which the trigger is specified. For each delete statement that triggered an action
, the DELETED table is created. For each insert statement that triggered an action, the INSERTED table is
created. An update is trated as a as a delete followed by an insert, hance for each update statement that
triggers an action, the DELETED and then the INSERTED tables are created. The DELETED table contains
copies of rows that are deleted from the triggered table. The INSERTED table contains copies of rows that
are inserted into the triggered table. For an update operation, the data before modification goes to the
DELETED table and the data after modification goes to the INSERTED table
AFTER Triggers
After triggers fire after the triggering event has been processed. An AFTER trigger can be specified by
using the AFTER or FOR resrrved keyword. After trigger can be created on base tables.
In the above trigger, the IF UPDATE() is very important as we are interested in tracking chages only to the
sal column in emp. If the IF UPDATE(sal) is not used then the trigger block will get executed for
modifications to any column of emp table. And in that case, if sal is not modified, then in the audit table
values of sal_old and sal_new will be the same.
Implementing business logic using AFTER trigger:
INSTEAD OF TRIGGERS
They are fired instead of the triggering event. They are executed after the corresponding INSERTED and
DELETED tables are created, but before any integrity constraint or any other action is performed.
create table t1(c1 numeric, c2 numeric, c3 as c1*c2 persisted constraint abc check (c3<50))
Here, c3 is a computed column, hence you can neither insert values into it thurough the insert command,
nor can you update it through the update comand
Also
Only UNIQUE or PRIMARY KEY constraints can be created on computed columns, while CHECK,
FOREIGN KEY, and NOT NULL constraints require that computed columns be persisted.
In this case, the message “NOT ALLOWED” is displayed and not the error of the check constraint which
prooves that instead of triggers are executed after the corresponding INSERTED and DELETED tables are
created, but before any integrity constraint or any other action is performed.
Hence, the INSTEAD OF trigger could also be used for constraint checking, and hence, in this case even
the following table structure would have done :
create table t1(c1 numeric, c2 numeric, c3 as c1*c2)
Create table myemp(empno numeric(18, 0), empname varchar(50), grade tinyint, sal numeric(10,2),
code tinyint, city varchar(50) )
There can be only one FIRST and one LAST after trigger on a table. The sequence in which the other
AFTER triggers on that very table will be executed is undefined. As the INSTEAD of triggers are fired before
the modification is done to the underlying table, INSTEAD OF triggers cannot be specified as FIRST or
LAST.
SQL Server 2005 allows you to define triggers for DDL events as follows :
Create Trigger dp_trig
On database
For DROP_TRIGGER
As print ‘You are dropping a trigger. Not allowed’
Rollback
To enable/disable trigger s:
disable trigger ot1 on orders
enable trigger ot1 on orders
SQL Server offers many extensions to the SELECT statement that can be used for Decision Support
Operations. SQL extensions that are implemented in SQL Server 2005 for Business Intelligence can be
divided into 4 groups :
Ranking Functions
Thay generally return a number that specifies the rank of the current row among all rows
and that belongs to the specified group
TOP n clause
It provides retrieval of the first n rows of a query result(usually sorted using some criteria)
The Group By clause is used to group together rows that have the same or common value for the
column/columns placed in the Group By clause in order to retrieve some aggregated/consolidated value for
each such group of rows.
Consider a table having score of maths for students of different divisions of different standards of
different schools
select sclcode, std, div, max(maths) from students group by sclcode, std, div with Rollup
ROLLUP does additional grouping considering the last column(nth column) as one column and the
remaining columns(1 to n-1 columns) as a single column, and then repeats the process for columns 1 to
columns n-1
Apart from the sum of marks for each DIV within each STD within each SCH(like the normal
GROUP BY), it will also show us the sum of marks for each STD within each SCH, sum of marks for each
SCH, and the Grand sum for all the students.
The group hierarchy using ROLLUP is determined by the order in which the columns are specified
in the group by clause
select sclcode, std, div, max(maths) from students group by sclcode, std, div with Cube
Apart from the sum of marks for each DIV within each STD within each SCH(like the normal
GROUP BY), it will also show us the sum of marks for each STD within SCH, sum of marks for each DIV
within a SCH, sum of marks for each DIV within a STD, sum of marks for each SCH, sum of marks for each
STD, sum of marks for each DIV and the Grand sum for all the students.
Thus, CUBE does additional grouping on all the combinations of the n columns involved in the
Group By clause
Ranking Functions
SQL Server 2005 defines four functions that are categorised as ranking functions, i.e., functions that return a
ranking value for each row in a partition group
RANK
The rank function returmns a number that specifies the rank of the row among all the rows
This example uses the OVER clause : over(order by sal desc) to sort the result set by the sal column in the
descending order.
The RANK function uses logical aggregation. In other words, if 2 or more rows in a resultset are tied(have a
same value in the ordering column), they will have the same rank. The row with the subsequent ordering will
have a rank that is one plus the number of ranks that precede the row. For this reason, the RANK function
displays gaps if two or more rows have the same ranking.
DENSE_RANK
This function is similar to the RANK() fucntion, except that it returns no gap if two or more ranking values are
equal and thus belong to the same ranking.
ROW_NUMBER
This function returns the sequential number of a row within a result set, starting at 1 for the first row.
The OVER clause is used in the above examples to determine the ordering of the resultset. This clause is
not used only for ordering. Generally, the OVER clause is used to divide the result set produced by the
FROM clause into groups(partitions) using the PARTITION BY, and the apply the ranking function to
each such partition separately as follows :
select rank() over(partition by deptno order by sal desc)as rank_sal, emp.* from emp
select dense_rank() over(partition by deptno order by sal desc) as d_rank_sal, emp.* from emp
select row_number() over(partition by deptno order by sal desc) as rownum, emp.* from emp
select row_number() over(partition by deptno order by deptno,secno) as dsrownum, emp.* from emp
The main difference between the use of GROUP BY clause and the grouping using the PARTITION BY
clause of the OVER clause is that OVER clause displays each of the rows from a group(partition)
separately, while the GROUP BY clause displays only one row for each group as follows :
Following query calculates the percentage of the salary of each employee in relation to the total salary of the
corresponding partition(department)
You may use several columns from a table to build different partitioning schemas in a query as follows :
select ename, sal,deptno,secno, dense_rank() over(partition by deptno order by sal desc) as d_rank_sal,
dense_rank() over(partition by deptno,secno order by sal desc) as ds_rank_sal from emp
TOP n
This clause specifies the first n rows of the query result that are to be retrieved
The TOP n clause is a part of the SELECT list and is written in front of all the column names in the SELECT
list. The TOPn clause can also be used with the additional PECENT option, in which case the first n percent
of the rows are retrieved from the result set.
The additional option WITH TIES specifies that additional rows will be retrieved from the query result if they
have the same value in the ORDER BY column(s) as the last row that belongs to the displayed set. The
WITH TIES option can be used only with the ORDER BY clause.
SQL Server 2005 allows you to use the TOP n clause with the update, delete and insert statements
update top(4) emp set sal=100 where sal in (select top 10 sal from emp order by sal asc)
delete top(10) percent from emp where sal in (select top 50 percent emp.sal from emp order by sal desc)
Create a table emp11 which is structurally same as that of emp table as follows :
CREATE TABLE emp11( empno numeric(5, 0) NULL, ename varchar(50)NULL, sal numeric(10, 2) NULL,
deptno numeric(3, 0) NULL, secno char(4) NULL
)
insert top(5) into emp11 select top 10 emp.* from emp order by sal desc
This means that the unique values returned by the PIVOT COLUMN MONTH column themselves become
fields in the final result set. As a result, there is a column for each MONTH number specified in the pivot
clause - in this case the month values 1,2 and 7. The BUDGET column serves as the VALUE COLUMN,
against which the columns returned in the final output, called the grouping columns, are grouped. In this
case, the grouping columns are aggregated by the SUM function.
UNPIVOT
UNPIVOT performs almost the reverse operation of PIVOT, by rotating columns into rows.
CREATE TABLE pvt (VendorID int, Emp1 int, Emp2 int, Emp3 int, Emp4 int, Emp5 int)
Here the UNPIVOT COLUMNS Emp1, Emp2, Emp3, Emp4 and Emp5 are converted into Rows under the
Column Heading EMPLOYEE and the values of the UNPIVOT COLUMNS Emp1, Emp2, Emp3, Emp4
and Emp5 are stored under the head ORDERS
In This Article we will see how to create trigger in SQL
server 2005.
Types of Triggers
Syntax:
create trigger triggername
on tablename
AFTER INSERT
As
[SQL Statement/PRINT command]
GO
Eg:
create trigger afterinsert_trigger
on emp
AFTER INSERT
as
PRINT 'AFTER TRIGGER EXECUTED SUCESSFULLY'
GO
on emp
AFTER UPDATE
as
GO
On emp
AFTER DELETE
as
GO
Instead Of Update Trigger