三 索引
在数据库中,索引使数据库程序无须对整个表进行扫描,就可以在其中找到所需数据。书中的索引是一个词语列表,其中注明了包含各个词的页码。而数据库中的
索引是一个表中所包含的值的列表,其中注明了表中包含各个值的行所在的存储位置。
设计索引要考虑的准则包括:
• 一个表如果建有
大量索引会影响 INSERT、UPDATE 和 DELETE 语句的性能,因为在表中的数据更改时,所有索引都须进行适当的调整。另一方面,对于不需要修改数据的查询(SELECT 语句),大量索引有助于提高性能。
•
覆盖的查询可以提高性能。覆盖的查询是指查询中所有指定的列都包含在同一个索引中。例如,如果在一个表的 a、b 和 c 列上创建了组合索引,则从该表中检索 a 和 b 列的查询被视为覆盖的查询。创建覆盖一个查询的索引可以提高性能,因为该查询的所有数据都包含在索引自身当中;检索数据时只需引用表的索引页,不必引用数据页,因而减少了 I/O 总量。
•
对小型表进行索引可能不会产生优化效果,因为 SQL Server 在遍历索引以搜索数据时,花费的时间可能会比简单的表扫描还长。
• 可以在
视图上指定索引。
• 可以在
计算列上指定索引。
使用聚集索引: 聚集索引确定表中数据的物理顺序。聚集索引类似于电话簿,后者按姓氏排列数据。由于聚集索引规定数据在表中的物理存储顺序,一个表只能包含一个聚集索引。但该索引可以包含多个列(组合索引)。
使用非聚集索引: 非聚集索引与课本中的索引类似。数据存储在一个地方,索引存储在另一个地方,索引带有指针指向数据的存储位置。索引中的项目按索引键值的顺序存储,而表中的信息按另一种顺序存储(这可以由聚集索引规定)。如果在表中未创建聚集索引,则无法保证这些行具有任何特定的顺序。
使用唯一索引: 唯一索引可以确保索引列不包含重复的值。
CREATE NONCLUSTERED INDEX DescIdx ON
ObjTable(ObjName ASC, ObjWeight DESC)
四 视图
视图是一个
虚拟表,其内容由查询定义。同真实的表一样,视图包含一系列带有名称的列和行数据。视图并不在数据库中以存储的数据值集形式存在。行和列数据来自由定义视图的查询所引用的表,并且在引用视图时动态生成。
定
义视图的筛选可以来自当前或其它数据库的一个或多个表,或者其它视图。如果有几台不同的服务器分别存储组织中不同地区的数据,而您需要将这些服务器上相似结构的数据组合起来,这种方式就很有用。
创建索引视图:若经常在查询中引用这类视图,可通过在视图上创建唯一聚集索引来提高性能。在视图上创建唯一聚集索引时将执行该视图,并且结果集在数据库中的存储方式与带聚集索引的表的存储方式相同。
创建分区视图:分区视图在一个或多个服务器间水平连接一组成员表中的分区数据,使数据看起来就象来自一个表。
创建分布式分区视图,首先应当:为 Server2 添加一个名为 Server2 的、
带有连接信息的链接服务器定义,并添加一个名为 Server3 的链接服务器定义以访问 Server3。然后在每个成员服务器上定义一个分布式分区视图,并且每个视图具有相同的名称。这样,引用分布式分区视图名的查询可以在任何一个成员服务器上运行。
CREATE VIEW Customers AS
SELECT * FROM 服务器1.数据库名.表的拥有者.表名(Customers_33)
UNION ALL
SELECT * FROM Server2.CompanyDatabase.TableOwner.Customers_66
UNION ALL
SELECT * FROM Server3.CompanyDatabase.TableOwner.Customers_99
五 存储过程
Transact-SQL 编程语言是应用程序和 SQL Server 数据库之间的主要编程接口。使用 Transact-SQL 程序时,可用两种方法存储和执行程序:可以在
本地存储Transact-SQL程序,并创建向 SQL Server 发送命令并处理结果的应用程序;也可以
将Transact-SQL程序在 SQL Server 中存储为存储过程,并创建执行存储过程并处理结果的应用程序。
可使用 Transact-SQL EXECUTE 语句运行存储过程。存储过程与函数不同,因为存储过程不返回取代其名称的值,也不能直接用在表达式中。
创建存储过程时,应指定:
1.指定参数:所有
输入参数和向调用过程或批处理返回的输出参数。
2.设计存储过程:
执行数据库操作(包括调用其它过程)的编程语句。
3.从存储过程中返回数据:返回结果集或返回至调用过程或批处理以表明成功或失败(以及失败原因)的
状态值。
CREATE PROC showind3 @table varchar(30) = NULL
AS IF @table IS NULL
PRINT 'Give a table name'
ELSE
SELECT TABLE_NAME = sysobjects.name,
INDEX_NAME = sysindexes.name, INDEX_ID = indid
FROM sysindexes INNER JOIN sysobjects
ON sysobjects.id = sysindexes.id
WHERE sysobjects.name = @table
六 用触发器强制执行业务规则
SQL Server提供了两种主要机制来强制业务规则和数据完整性:约束和触发器。触发器是一种特殊类型的存储过程,它在指定的表中的数据发生变化时自动生效。唤醒调用触发器以响应 INSERT、UPDATE 或 DELETE 语句。触发器可以查询其它表,并可以包含复杂的 Transact-SQL 语句。将触发器和触发它的语句作为可在触发器内回滚的单个事务对待。
触发器可以支持约束的所有功能,在约束所支持的功能无法满足应用程序的功能要求时,触发器就极为有用。
设计触发器:
• 执行 INSTEAD OF 触发器代替通常的触发动作。
INSTEAD OF 触发器还可在带有一个或多个基表的视图上定义,而在这些视图上这些触发器可扩展视图可支持的更新类型。
• 在执行了 INSERT、UPDATE 或 DELETE 语句操作之后执行
AFTER 触发器。AFTER 触发器只能在表上指定。
创建触发器时需指定:
• 名称。
• 在其上定义触发器的表。
• 触发器将何时激发。
• 激活触发器的数据修改语句。有效选项为 INSERT、UPDATE 或 DELETE。多个数据修改语句可激活同一个触发器。例如,触发器可由 INSERT 或 UPDATE 语句激活。
• 执行触发操作的编程语句。
CREATE TABLE my_table*
(a int NULL, b int NULL)
GO
CREATE TRIGGER my_trig
ON my_table
FOR INSERT
AS
IF UPDATE(b)
PRINT 'Column b Modified'
GO
七 用户定义函数
函数是由一个或多个 Transact-SQL 语句组成的子程序,可用于封装代码以便重新使用。SQL Server并不将用户限制在定义为 Transact-SQL 语言一部分的内置函数上,而是允许用户创建自己的用户定义函数。
CREATE FUNCTION CubicVolume
-- Input dimensions in centimeters
(@CubeLength decimal(4,1), @CubeWidth decimal(4,1),
@CubeHeight decimal(4,1) )
RETURNS decimal(12,3) -- Cubic Centimeters.
AS
BEGIN
RETURN ( @CubeLength * @CubeWidth * @CubeHeight )
END
然后可以在允许整型表达式的任何地方(如表的计算列中)使用该函数:
CREATE TABLE Bricks
(
BrickPartNmbr int PRIMARY KEY,
BrickColor nchar(20),
BrickHeight decimal(4,1),
BrickLength decimal(4,1),
BrickWidth decimal(4,1),
BrickVolume AS
(
dbo.CubicVolume(BrickHeight,BrickLength, BrickWidth)
)
)