标题:[经验]SQL应用实例
只看楼主
Kendy123456
Rank: 10Rank: 10Rank: 10
等 级:贵宾
威 望:62
帖 子:2720
专家分:0
注 册:2007-1-3
 问题点数:0 回复次数:43 
[经验]SQL应用实例

开这篇贴的目的是让大家就实例来交流SQL中, 那些平常不怎么被人所使用而其实很有用的命令.

希望大家把自己的心得和经验都贡献出来 然后让版主固顶.

我先来抛块砖:

一. 创建表的时候 使用计算列
CREATE TABLE t1
(P int IDENTITY(1,1),
C int NOT NULL,
M int NOT NULL,
T AS (C+ M)
)

insert into t1 values(1,2)
select t from t1

P C M T
----------- ----------- ----------- -----------
1 1 2 3

(1 row(s) affected)

这里T就是一个计算列. Insert Update语句都不能对计算列字段操作,但是select语句可以从该列取得值.
创建计算列有什么用呢? 可以用于视图的触发器中.
一个视图,是多个表的数据结合在一起显示的.
比如我们创建2个表,存放Employee的FirstName和LastName:

create table name1
(
EmployeeID int PRIMARY KEY,
Firstname varchar(100)
)
create table name2
(
EmployeeID int,
Lastname varchar(100)
)
再创建一个显示Employee全名的view
CREATE VIEW vw_Employee_FullName
AS
SELECT a.EmployeeID, FirstName + ';' + LastName AS FullName
FROM Name1 a join Name2 b on a.EmployeeID =b.EmployeeID

这时候设计一个视图的update操作的instead of触发器
CREATE TRIGGER InsteadInsertName on vw_Employee_FullName
INSTEAD OF INSERT
AS
BEGIN
INSERT INTO Name1 (EmployeeID,Firstname)
SELECT EmployeeID,LEFT(FullName,(CHARINDEX(';', FullName) - 1))
FROM inserted

INSERT INTO Name2 (EmployeeID,Lastname)
SELECT EmployeeID,RIGHT(FullName,LEN(FullName)-CHARINDEX(';', FullName))
FROM inserted
END

这样 从前台插入employee新数据的时候,我们只要把向view中插入就可以了,由view的触发器来向2个表中插入数据
insert into vw_Employee_FullName values (1,'George;Bush')
select * from name1
select * from name2

EmployeeID Firstname
----------- ----------------------------------------------------------------------------------------------------
1 George

(1 row(s) affected)

EmployeeID Lastname
----------- ----------------------------------------------------------------------------------------------------
1 Bush

(1 row(s) affected)


二. 外键之间的级联操作
通常情况下,我们使用外键时,在插入和删除数据的时候一定要注意顺序,插入时要先主表再从表, 删除时要先从表再主表,更新时还不能任意更新外键中的列.
外键也是约束,这些限制是为了保证数据库数据的完整性和一致性,写代码的时候往往一不注意就会得到异常.
实际上系统也允许另外一种工作方式: 更改外键的列时候,主动更新外键关联的其它表的相关列.
创建外键时 用 ON DELETE { CASCADE | NO ACTION },ON Update { CASCADE | NO ACTION }声明是否启用级联操作 默认是NO Action.
ON DELETE NO ACTION
指定如果试图删除某行,而该行含有由其它表的现有行中的外键所引用的键,则产生错误并回滚 DELETE。

ON UPDATE NO ACTION
指定如果试图更新某行中的键值,而该行含有由其它表的现有行中的外键所引用的键,则产生错误并回滚 UPDATE。

ON DELETE CASCADE
指定如果试图删除某行,而该行含有由其它表的现有行中的外键所引用的键,则也将删除所有包含那些外键的行。如果在目标表上也定义了级联引用操作,则对从那些表中删除的行同样采取指定的级联操作。

ON UPDATE CASCADE
指定如果试图更新某行中的键值,而该行的键值由其它表的现有行中的外键所引用,则所有外键值也将更新成为该键指定的新值。如果在目标表上也定义了级联引用操作,则对在那些表中更新的键值同样采取指定的级联操作。

仍然以上面的例子,重新创建name2 并建立外键
Drop table name2
CREATE TABLE Name2
(
EmployeeID int primary key FOREIGN KEY REFERENCES Name1(EmployeeID) ON DELETE Cascade ON Update Cascade,
Lastname varchar(100)
)

update name1 set EmployeeID = 3 where EmployeeID = 1

select * from name1
select * from name2

(1 row(s) affected)

EmployeeID Firstname
----------- ----------------------------------------------------------------------------------------------------
3 George

(1 row(s) affected)

EmployeeID Lastname
----------- ----------------------------------------------------------------------------------------------------
3 Bush

(1 row(s) affected)

****注意 不要试图去update name2, 那是不合法的. 仅仅允许更新外键中主表的列, 并且更新自动传递到子表.

delete name1 where EmployeeID = 3

select * from name1
select * from name2

EmployeeID Firstname
----------- ----------------------------------------------------------------------------------------------------

(0 row(s) affected)

EmployeeID Lastname
----------- ----------------------------------------------------------------------------------------------------

(0 row(s) affected)

**** 注意 这里delete name2也是合法的 但是不会影响到主表name1.

级联是允许多级的, 假如还有表name3, 以name2为主表建立了外键:

CREATE TABLE Name3
(
EmployeeID int FOREIGN KEY REFERENCES Name2(EmployeeID) ON DELETE Cascade ON Update Cascade,
MiddleName varchar(100)
)

那么对name1 的EmployeeID做update, 或者删除行的会, name3也会做同样操作
SQL帮助上是这样描述的:
由单个 DELETE 或 UPDATE 触发的一系列级联引用操作必须构成不包含循环引用的树。
在 DELETE 或 UPDATE 所产生的所有级联引用操作的列表中,每个表只能出现一次。
级联引用操作树到任何给定表的路径必须只有一个。
树的任何分支在遇到指定了 NO ACTION 或默认为 NO ACTION 的表时终止。

搜索更多相关主题的帖子: SQL 实例 经验 int 应用 
2007-01-30 16:43
accpfriend
Rank: 3Rank: 3
等 级:论坛游侠
威 望:5
帖 子:167
专家分:102
注 册:2006-12-31
得分:0 
2007-01-30 16:46
棉花糖ONE
Rank: 7Rank: 7Rank: 7
等 级:贵宾
威 望:32
帖 子:2987
专家分:0
注 册:2006-7-13
得分:0 
楼主帅哥,怎么固顶啊,不会

26403021 sql群 博客 blog./user15/81152/index.shtml
2007-01-30 16:49
Kendy123456
Rank: 10Rank: 10Rank: 10
等 级:贵宾
威 望:62
帖 子:2720
专家分:0
注 册:2007-1-3
得分:0 
楼上的...IE右下角... 管理选项: 专题管理 | 锁定 | 提升 | 沉底 | 跟贴管理 | 删除 | 移动 | 设置固顶 | 发布公告

2007-01-30 16:54
zjcyzw
Rank: 1
等 级:新手上路
帖 子:1
专家分:0
注 册:2007-2-1
得分:0 
好啊
2007-02-02 09:30
gangdou1998
Rank: 1
等 级:新手上路
帖 子:4
专家分:0
注 册:2007-2-2
得分:0 
支持下!
2007-02-02 17:05
ninggang
Rank: 3Rank: 3
等 级:新手上路
威 望:6
帖 子:637
专家分:0
注 册:2006-11-1
得分:0 

哈哈,又熟悉了一遍
支持!!!


大家一起努力,共同打造未来!!
2007-02-05 12:54
maggie_82
Rank: 1
等 级:新手上路
帖 子:33
专家分:0
注 册:2007-1-2
得分:0 

学习中

2007-03-12 12:43
帅哥一条虫
Rank: 1
等 级:新手上路
威 望:1
帖 子:65
专家分:0
注 册:2006-10-15
得分:0 
2007-03-17 14:26
bayishi
Rank: 1
等 级:新手上路
帖 子:52
专家分:0
注 册:2007-3-17
得分:0 

这几天才开始SQL所以有点看不懂..不过我会努力向上的

2007-03-18 10:59



参与讨论请移步原网站贴子:https://bbs.bccn.net/thread-118886-1-1.html




关于我们 | 广告合作 | 编程中国 | 清除Cookies | TOP | 手机版

编程中国 版权所有,并保留所有权利。
Powered by Discuz, Processed in 0.239055 second(s), 7 queries.
Copyright©2004-2024, BCCN.NET, All Rights Reserved