日期:2014-05-19  浏览次数:22880 次

[原创]SQLServer陷阱
本文旨在指出一些在使用SQLServer过程中容易犯的错误, 希望能给您带来帮助.
若没有特殊说明, 本文是指在MS SQLServer 2000简体中文版的默认配置环境中.

一, NULL与布尔数据类型
Transact-SQL中存在Boolean类型, if 后面的表达式的计算结果一般是Boolean类型, 但无法使用 declare 定义Boolean类型的变量.

Boolean数据类型有三种取值, TRUE, FALSE, UNKNOWN, 第3种取值通常会被人忽视从而导致逻辑错误.
默认情况下SET ANSI_NULLS为ON, 在逻辑表达式中如果你忽略了NULL的存在, 结果可能会异于你所想.
例1: 
SQL code

declare @a int
if (@a > 0)
    set @a = 1
else if not (@a > 0)
    set @a = 2
else
    set @a = 3


结果@a的值应该是3, 因为NULL>0的值为UNKNOWN, NOT UNKNOWN的值还为UNKNOWN.
例2:
SQL code

declare @a int
if @a = null
    set @a = 1
else if @a = null or 1 = 1
    set @a = 2
else
    set @a = 3


结果@a的值应该是2, 因为NULL = 0的值为UNKNOWN, UNKNOWN or TRUE的值为TRUE.

二, 运行时错误与自动回滚事务
有些人认为一个批查询在执行中发生了错误, 这个查询就会中止, 其实是错误的.

例1:
SQL code

declare @i int
set @i = 1 / 0
set @i = 1
select @i


结果会先报一个
服务器: 消息 8134,级别 16,状态 1,行 2
遇到被零除错误。
然后输出结果集 1.

例2:
SQL code

set xact_abort on
declare @i int
set @i = 1 / 0
set @i = 1
select @i


结果只报错, 不会输出结果.

例3:
请在查询分析器中新建连接执行
SQL code

create table table1(id int primary key)

begin tran
insert into table1 values (1)
insert into table1 values (1)
insert into table1 values (2)
commit tran


第二个insert会产生违反主键约束错误, 但是执行结束后你会发现事务已经提交并且table1中已经有两行记录1与2

例4:
SQL code

set xact_abort on

create table table2(id int primary key)

begin tran
insert into table2 values (1)
insert into table2 values (1)
insert into table2 values (2)
commit tran


执行结束后, table2中没有记录, 说明事务已经回滚.

当 SET XACT_ABORT 为 ON 时,如果 Transact-SQL 语句产生运行时错误,整个事务将终止并回滚。为 OFF 时,只回滚产生错误的 Transact-SQL 语句,而事务将继续进行处理。编译错误

(如语法错误)不受 SET XACT_ABORT 的影响。
一般批查询中 SET XACT_ABORT 默认为 OFF, 隐式开启的事务如触发器中SET XACT_ABORT 默认为ON

未完...

------解决方案--------------------
好,看看
------解决方案--------------------
sf
------解决方案--------------------
不用回答,甚好。
------解决方案--------------------
up
------解决方案--------------------
.
------解决方案--------------------
看看,支持原创
------解决方案--------------------
...
------解决方案--------------------
还有吗?
------解决方案--------------------
...
------解决方案--------------------
mark
------解决方案--------------------
up
------解决方案--------------------
look
------解决方案--------------------