1、北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3. 数据库应用程序体系结构,数据库系统是指在计算机系统中引入数据库后的系统,一般由数据库、数据库管理系统、应用系统、DBA、用户组成。 本章介绍数据库应用程序的数据访问与数据库应用系统的体系结构。3.1嵌入式SQL3.2事务处理技术3.3数据库应用系统体系结构3.4中间件,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1 嵌入式SQL,为什么使用嵌入式SQL? 有些数据访问任务对于交互式的非过程的SQL是无法完成的任务。 使用交互式SQL,必须知道表名、列名并且能够写出符合语法的SQL语句。 实际的
2、应用系统是非常复杂的,数据库访问只是其中一个部件。有些动作如与用户交互、图形化显示数据等只能用高级语言实现。 嵌入到过程性主语言中使用的SQL称为嵌入式SQL。主语言可以是C或Java(不一定是Windows环境).也可以是Visual Basic, Delphi (Windows环境)等。 ORACLE的Pro*C即是使用嵌入式SQL的平台。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1 嵌入式SQL,把SQL嵌入主语言使用时必须解决的三个问题:1区分 SQL语句与主语言语句,用EXEC SQL开始.2数据库工作单元和程序工作单元之间的通信.SQL语句可以使用主
3、语言的程序变量(简称主变量),这些变量名前加冒号(:)作标志,以区别于字段名。这些变量由BEGIN DECLARE SECTION与END DECLARE SECTION语句之间说明.主语言中不能引用数据库中的字段变量.SQL语句执行后,系统要反馈给应用程序若干信息,这些信息送到SQL的通信区SQLCA。SQLCA 用语句EXEC SQL INCLUDE加以定义。3一个SQL语句原则上可产生或处理一组记录,而主语言一次只能处理一个记录,为此必须协调两种处理方式。这是用游标来解决的。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1 嵌入式SQL,主语言 + 嵌入SQL
4、,预处理,主语言 + 函数调用,主语言编译器,主语言执行程序,预处理器把嵌入的SQL语句从主程序命令中分离出来,转换成相应的主语言语句. 例: 1.UNIX环境下,程序员创建包含SQL的main.pc的源程序. 2.Oracle程序员调用预编译器:proc iname=main.pc生成main.c,其中SQL语句被纯c语句(Orcale运行期库函数)替换. 3.主语言编译cc -c main.c,生成main.o目标文件. 4. 连编生成可执行文件.,嵌入式SQL的执行,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.1 C语言中嵌入式SQL,#include #
5、include “prompt.h” exec sql include sqlca; /*声明通讯区*/ char cid_prompt=“请输入顾客号:”; int main( ) exec sql begin declare section; char cust_id5,cust_name14;float cust_discnt;char user_name20,user_ped20;exec sql end declare section;/*声明变量*/exec sql whenever sqlerror goto report_error;exec sql whenever not
6、found goto notfound;/*出错处理*/strcpy(user_name,”mytest”);strcpy(user_pwd,”test”);exec sql connect :user_name identified by :user_pwd; /*连接*/,while(prompt(cid_prompt,1,cust_id,4)=0) exec sql select cname,discntinto :cust_name,:cust_discntfrom customers where cid=:cust_id;exec sql commit work;printf(“顾客
7、名: %s 折扣率: %5.1fn”,cust_name,cust_discnt);continue; notfound: printf(“没找到 %s,继续n”,cust_id); /*根据输入的顾客ID查询顾客信息*/ exec sql commit release; /*正常释放连接*/ return 0;report_error:print_dberror(); /*出错信息*/exec sql rollback release; /*释放连接*/return 1; ,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.1 C语言中嵌入式SQL,区分SQL语句与
8、C语言语句 嵌入的SQL语句以EXEC SQL开始,以分号(;)结束。 例:exec sql select came,discnt into :cust_name,:cust_discnt from customers where cid=:cust_id; 嵌入SQL语句与C语言之间的数据传递 宿主变量(宿主变量出现于SQL语句中时,前面加(:)以区别列名) C变量既可以用在C语句中,也可用在SQL语句中, 用来在两者之间传递数据。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.1 C语言中嵌入式SQL,宿主变量的声明在嵌入式SQL语句中使用宿主变量,必须先声明
9、它们:声明为通常的C变量,并将其放在下列标识语句之间,EXEC SQL BEGIN DECLARE SECTIONEXEC SQL END DECLARE SECTION例: exec sql begin declare section;char cust_id5=c001;char cust_name14;float cust_discnt;exec sql end declare section;,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.1 C语言中嵌入式SQL,在SQL中建立连接和释放连接在一个嵌入式SQL程序开始,程序面临着和交互式用户同样的问题:怎
10、样与数据库建立连接.例: exec sql begin declare section; /*声明变量*/char user_name10,user_ped10;exec sql end declare section;strcpy(user_name,mytest); /*变量赋值*/strcpy(user_pwd,test);exec sql connect :user_name identified by :user_pwd; /*Oracle连接*/例:exec sql commit release;/*Oracle断开连接*/exec sql rollback release;/*O
11、racle断开连接*/,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.2 游标,SQL与主语言之间操作方式的协调SQL:一次一集合。C语言:一次一记录。 游标:在查询结果的记录集合中移动的指针。若一个SQL语句返回单个元组,则不用游标。若一个SQL语句返回多个元组,则使用游标。 不需要游标的数据操作 结果是一个元组的select语句exec sql select came,discnt into :cust_name,:cust_discnt from customers where cid=:cust_id;,北京邮电大学软件学院 郭文明 2003.06,数据库
12、设计与开发讲义,3.1.2 游标,需要游标的数据操作当select语句的结果中包含多个元组时,使用游标可以逐个存取这些元组。活动集:select语句返回的元组的集合。当前行:活动集中当前处理的那一行。游标即是指向当前行的指针。游标分类: 滚动游标:游标的位置可以来回移动,可在活动集中取任意元组。 非滚动游标:只能在活动集中顺序地取下一个元组。 更新游标:数据库对游标指向的当前行加锁,当程序读下一行数据时,本行数据解锁,下一行数据加锁。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.2 游标,定义一个游标,使之对应一个select语句DECLARE 游标名 SCRO
13、LL CURSORFOR select语句 for update of列表名for update任选项,表示该游标可用于对当前行的修改与删除。 打开一个游标,执行游标对应的查询,结果集合为该游标的活动集。OPEN 游标名在游标被声明之后,它仍然不是活动状态,在程序开始检索信息之前,执行SQL的OPEN语句打开这个游标,游标被打开之后,可使用取(fetch)操作从游标中每次检索一行,程序完成检索后,应关闭游标,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.2 游标,在活动集中将游标移到特定的行,并取出该行数据放到相应的宿主变量中。FETCH NEXT | PRIOR
14、 | FIRST | LAST | CURRENT | RELETIVE n | ABSOLUTE n 游标名 INTO 宿主变量表关闭游标,释放活动集及其所占资源。需要再使用该游标时,执行open语句。CLOSE 游标名 删除游标,以后便不能再对该游标执行open语句了.FREE 游标名,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.2 游标,#define ture 1 #include #include “prompt.h” exec sql include sqlca; /*声明通讯区*/ int main( ) char cid_prompt=“请输入顾
15、客号:”;exec sql begin declare section; char cust_id5,agent_id4;double dollar_sum;char user_name20,user_ped20;exec sql end declare section; /*声明变量*/exec sql declare agent_dollars cursor for select aid,sum(dollars) from orderswhere cid=:cust_id group by aid;/*游标*/exec sql whenever sqlerror goto report_e
16、rror;exec sql whenever not found goto finish;/*出错处理*/strcpy(user_name,”mytest”);strcpy(user_pwd,”test”);,exec sql connect :user_name identified by :user_pwd; /*连接*/ while(prompt(cid_prompt,1,cust_id,4)=0)exec sql open agent_dollars;while (ture) exec sql fetch agent_dillars into:agent_id,:dollar_sum;
17、 /*游标取值*/printf(“ %s %11.2fn”,agent_id,dollar_sum);continue; finish: exec sql close agent_dollars; exec sql commit work; /*游标关闭*/ /*输入顾客ID的代理商和金额*/ exec sql commit release; /*正常释放连接*/return 0; report_error:print_dberror(); /*出错信息*/exec sql rollback release; /*释放连接*/return 1; ,北京邮电大学软件学院 郭文明 2003.06,
18、数据库设计与开发讲义,3.1.3 通讯区,SQL语句执行信息反馈 良好的应用程序必须提供对错误的处理,应用程序需要知道SQL语句是否正确执行了,发生错误时的错误代码,执行时遇到特殊情况时的警告信息。 SQL通讯区SQLCA是一个已被声明过的内存结构,每一嵌入SQL语句的执行情况在其执行完成后写入USERCA结构中的各变量中, 根据SQLCA中的内容可以获得每一嵌入SQL语句执行后的信息,应用程序就可以做相应的处理。 为了说明 (USERCA),必须在应用程序中包括:EXEC SQL INCLUDE SQLCA;,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.3 通
19、讯区,SQLCODE:SQLCODE是SQLCA的结构一个成员。它是一个每次执行完SQL语句都被更新的整型变量。 如果执行成功,SQLCODE为0; 如果语句没有产生错误,但遇到了没有数据,SQLCODE为100; 除去成功返回0或没有数据返回100的情况,其他都是某种错误并返回一个负数。 SQL-99和X/OpenSQL等标准提倡用SQLSTATE取代SQLCODE检测SQL的执行情况,并将SQLSTATE设置为标准,但在产品中还不一定支持。例如ORACLE中,预处理程序运行时必须设置MODE=ANSI才能支持SQLSTATE.,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发
20、讲义,3.1.3 通讯区,SQLSTATE:SQLSTATE作用与SQLCODE作用相同,但它是在标准方式下起作用。SQLCODE是一个整数,SQLSTATE是一个长度为5的只能由A到Z字符和0到9数字组成的字符串。5个字符分为两组,前两个为类码,后三个为子类码。SQL标准规定:分类码的第一个字符可为A到H或0到4,这样分类主要为了统一,第一个字符为I到Z或5到9的分类码留给软件开发者去定义。分类码00指成功,01指成功但产生一个警告,02指没有数据,等价于SQLCODE的100,非00、01和02指语句没有成功完成。可以查阅数据库系统产品的嵌入式SQL参考指南得到SQLSTATE、SQLCO
21、DE、SQLCA,确定主要的出错条件,以它们的报告方式。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.4 错误处理,Whenever语句使我们在遇到出错和其他情况时,控制程序的运行:EXEC SQL WHENEVER 条件 动作条件可以是 SQLERROR:执行错误,如连接不成功等; NOT FOUND:没有数据,如游标指针到头或到尾等; SQLWARNING:警告错误。动作可以是 CONTINUE:继续正常流程; GOTO 标号:转移到标号行继续执行; STOP:结束程序,撤消当前事务,并断开数据库连接; DO 函数:引发一个对已经命名的函数的调用。,北京邮电
22、大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.4 错误处理,没有WHENEVER语句时缺省动作是Continue. 如果SQLCODE为负,则SQLERROR为真,如果SQLCODE为100或SQLSTATE为02000,则NOT FOUND为真。抽取错误信息的确切代码依赖于所使用的数据库系统。 WHENEVER语句的主要价值在于减少处理错误的代码行数,另外WHENEVER的语法可以在不同数据库系统之间进行最大限度的移植。例如利用检测条件NOT FOUND在不同数据库产品中可能有不同的sqlca.sqlcode值,但NOT FOUND却始终表示没有发现记录这一错误。,北京
23、邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.5 指示变量,如果一个宿主变量所对应的数据库字段允许空值,或字符串类型的宿主变量的长度可能小于所对应的数据库字段的长度,则需要一个指示变量来指明数据库访问的返回状态。 指示变量: 是一个C变量,用来指示返回给宿主变量的值是否为null值,以及返回给宿主变量的字符串是否发生了截断。指示变量的返回值:= 0:取到主变量的值不空,没有发生截断。= 1:取到主变量的值为空值。 0:取到主变量的值发生了截断,指示变 量的值是截断前的字符串的实际长度。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.5 指
24、示变量,指示变量的用法:声明与宿主变量的声明方式一样,在数据操纵语句中,在宿主变量和指示变量之间加( : )或关键字indicator。 例:exec sql begin declare sectionfloat cust_discnt;short int cd_ind;exec sql end declare sectionexec sql select discnt into :cust_discntindicator:cd_indfrom customers where cid=:cust_id; 在检索之后,如果cd_ind的值为-1,则变量cust_discnt得到了一个空值;如果为
25、0,则cust_discnt中的值是正常的。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.5 指示变量,不管读取数据还是更新数据,都可以用指示变量的值-1代表空值。 例:要将表customers的某一行的discnt值设置为空值,可以这样写:cd_ind=-1exec sql update customers set discnt=:cust_discntindicator :cd_ind where cid=:cust_id; 实际上还可以进一步扩展指示变量的值,例如DB2 UDB的产品中,如果指示变量的值为-2,意味着是由于一个错误而不是数据库中存储的值而使
26、检索到的值为空值。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.1.6 嵌入式SQL语句,检索:EXEC SQL SELECT ALL|DISTINCT 表达式 INTO 宿主变量 FROM 表名 WHERE 条件; 游标定义:EXEC SQL DECLEARE 游标名 CURSOR FOR 子查询 ORDER BY FOR READ ONLY |UPDATE OF 列名; 游标打开与关闭:EXEC SQL OPEN|CLOSE 游标名; 游标取值:EXEC SQL FETCH NEXT|PRIOR|FIRST|LAST |CURRENT|RELETIVE n|AB
27、SOLUTE n 游标名 INTO 宿主变量; 删除:EXEC SQL DELETE FROM 表名 WHERE条件|WHERE CURRENT OF 游标名; 修改:EXEC SQL UPDATE 表名 SET 列=表达式 WHERE 条件|WHERE CURRENT OF 游标名; 增加:EXEC SQL INSERT INTO 表名 (列名) VALUES(表达式);,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2 事务处理技术,保证数据的一致性和数据库的并行性,是衡量一个数据库的最基本和最重要的指标之一。一致性:以一致性规则为基础的数据逻辑关系。如转帐任务不
28、能造成帐户金额的不平衡。并行性:各个用户能够实现对数据库资源的共享。数据并发是多用户系统的基本要求,数据一致是因为有数据并发存在,为了适应多用户系统,协调管理数据库中的数据,保证各个用户的任务能够顺利准确地完成。事务处理是实现数据库一致性和并行性的重要手段。在保证一致性的前提下最大限度地提高并发度。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2 事务处理技术,数据操纵以SQL为基础,但单条SQL语句不一定能完成所有的用户请求,许多用户请求需要若干条SQL语句,而且这些语句有关联,要么全做,要么全不做。 如果许多用户的众多SQL语句不加控制,随意执行,必然破坏数据的
29、一致完整,出现丢失修改、不可重复读、读脏数据的错误。 数据库系统要对用户的操作进行控制(事务控制和封锁技术),保证并发的同时保证数据的一致。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.1 事务概念,事务是由一系列操作序列构成的程序执行单元,这些操作要么都做,要么都不做,是一个不可分割的工作单位。事务是数据库提供的一种手段,应用程序员将一系列操作组合在一起作为一个整体以便数据库系统提供保证。事务才是对数据库系统进行操作的最小合法单位。DBMS在事务级而不是在语句级确保数据的一致性。 事务以Begin transaction开始,以Commit work或Roll
30、back work结束。嵌入式SQL: EXEC SQL COMMIT WORK;EXEC SQL ROLLBACK WORK;,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.1 事务概念,Commit work表示提交,事务正常结束。Rollback work表示事务非正常结束,撤消事务已做的操作,回滚到事务开始时状态。事务的内容只限于数据更新操作(增删改),不包含其他SQL命令。在标准SQL中,没有Begin transaction语句,上一条Commit或Rollback或SQL修改命令即为事务的开始。有的DBMS使用Begin transaction作为事
31、务的开始。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.1 事务概念,事务特性(ACID) 原子性(Atomicity)事务的更新操作必须作为一个整体,其中包含的所有操作要么全做,要么全不做。原子性由系统恢复机制实现。 一致性(Consistency)事务的成功完成将数据库从一个一致状态转变到另一个一致状态。事务开始前,数据库处于一致性的状态;事务结束后,数据库必须仍处于一致性状态。数据库的一致性状态由用户来负责。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.1 事务概念,事务特性(ACID) 隔离性(Isolation)系统必须
32、保证事务不受其它并发执行事务的影响。对任何一对事务T1,T2,在T1看来,T2要么在T1开始之前已经结束,要么在T1完成之后再开始执行。隔离性通过并发控制机制实现。 持久性(Durability)一个事务一旦提交之后,它对数据库的影响必须是永久的,无论发生何种系统故障。持久性通过恢复机制实现。 事务的原子性、隔离性、持久性由数据库系统加以保证,一致性一般由程序员在编写程序中予以保证。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.2 事务的调度,事务的调度:DBMS在处理用户提交事务时的策略,即事务调度。事务的执行顺序称为一个调度,表示事务的指令在系统中执行的时间
33、顺序。 一组事务的调度必须保证 包含了所有事务的操作指令 一个事务中指令的顺序必须保持不变。 串行调度 在串行调度中,属于同一事务的指令紧挨在一起。 对于有n个事务的事务组,可以有n!个有效调度。 并行调度 在并行调度中,来自不同事务的指令可以交叉执行。 当并行调度等价于某个串行调度时,则称它是正确的。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.2 事务的调度,ANSI SQL-99标准中,一致性级别(隔离级别)的定义 serializable:一个调度的执行必须等价于一个串行调度的结果。 repeatable read:只允许读取已提交的记录,并要求一个事务
34、对同一记录的两次读取之间,其它事务不能对该记录进行更新。 read committed:只允许读取已提交的记录,但不要求可重复读。 read uncommitted:允许读取未提交的记录。 在SQL-99的语法中允许在启动事务的SQL语句之前设置隔离级别。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.3 事务的数据封锁,数据库管理系统采用数据封锁技术和事务技术解决并发性和一致性问题.数据封锁有两种封锁模式:专用锁:当一个事务以专用方式封锁某个资源时,只有此事务可以改变其中的内容,在该事务结束或释放其资源后,其它事务才能使用;共享锁:允许已封锁的资源被其它事务适度
35、共享,多个事务可以在同一资源上申请共享锁. 根据封锁的类型、持锁时间、何时释放的规则,将封锁协议分为一级封锁协议、二级封锁协议、三级封锁协议。不同封锁协议在不同程度上保证数据一致性和系统并发性。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.3 事务的数据封锁,在SQL语句执行时,所有必要的封锁均由DBMS自动完成(也可显式加锁),事务中所有为执行SQL语句建立的封锁均要延续到事务结束时才能释放,否则一个数据库对象在同一时间段内被多个事务交替操作,可能造成对数据库数据的破坏. 当参与封锁的事务较多,而每个事务封锁的资源也较多时,可能出现死锁情况。预防死锁的方法有一
36、次封锁法、顺序封锁法。 死锁的诊断有超时法、有向图法。死锁发生后,DBMS通常选择一个处理死锁代价最小的事务将其撤消,并恢复该事务。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.3 事务的数据封锁,两段锁协议(Two-phase Locking) 内容: 在对任何数据进行读写之前,事务首先要获得对该数据的封锁。 在释放一个封锁之后,事务不再获得任何其它封锁。即事务分为两个阶段:生长阶段:获得封锁。收缩阶段:释放封锁。 定理:若所有事务均遵从两段锁协议,则这些事务的所有并行调度都是可串行化的。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3
37、.2.4 ORACLE事务控制-回退段,ORACLE为了适应事务控制设置了回退段这一数据库对象.系统利用回退段来确保诸如读一致性、数据库恢复等管理功能。 ORACLE在缺省情况下,读数据不加锁,通过回退段(Rollback Segment)保证用户不读脏数据和可重复读. 表空间中的数据按段来组织,数据段、索引段、暂存段和回退段,回退段是一块磁盘存储区域,回退段可以由用户创建,但只能由系统进程使用。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.4 ORACLE事务控制-回退段,回退段中的数据是为事务服务的,每执行事务时,系统先在指定回退段上记录将要对数据进行的更改
38、,以事务为单位,各个事务的回退信息链接在一起。 当事务要回退时,利用回退信息将数据块中的数据恢复到先前的状态。 事务成功提交后,回退信息逐渐失效(在提交之前申请的查询需要这些信息保证读一致性,事务提交前对数据的变动不会为其他用户所知晓)。回退段可以循环使用。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.4 ORACLE事务控制-回退段,用回退段保证读一致性(不读脏数据和可重复读):,1,2,3,4,5,6,Tu2,Tu1,Ts3,Ts2,Ts1,时间,事务,表customers,数据缓冲区 cid discnt c001 10 1115,数据段:,回退段:,Tu
39、1,Tu2,例: 有5个事务并发: Ts1,Ts2,Ts3为查询事务, Tu1,Tu2为更新事务.Tu1:UPDATE customers SET discnt=discnt*1.1 WHERE cid=c001;Tu2: UPDATE customers SET discnt=15 WHERE cid=c001; 事务开始和完成时间段如右上图: 事务对回退段影响如右下图:,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.4 ORACLE事务控制-回退段,用回退段保证读一致性(不读脏数据和可重复读): 事务的开始顺序和基准时间为:Ts1=0 Tu1=3 Ts2=4
40、Tu2=5 Ts3=6;事务的完成顺序和基准时间为:Tu1=4 Tu2=6 Ts16 Ts26 Ts36;数据缓冲区的内容是最新更改的结果, 回退段按时间顺序记录了每次更改以前的数据; 尽管Tu1和Tu2两次更改了discnt的值, 但Tu1开始之前Ts1已开始,所以在时间4结束的Tu1回退信息并不马上消失,保证Ts1从回退段中查得discnt为10,Tu2开始之前Ts2已开始,所以在时间6结束的Tu2回退信息并不马上消失,保证Ts2从回退段中查得discnt为11, Ts3基准时间是6,从缓冲区中查得discnt为15.Ts1和Ts2结束后才清除回退段信息.,北京邮电大学软件学院 郭文明 2
41、003.06,数据库设计与开发讲义,3.2.4 ORACLE事务控制-回退段,在数据库创建时SYSTEM表空间中建立了SYSTEM回退段。每个数据库可以有一个或多个回退段,最好只将SYSTEM回退段用于系统事务,将用户事务分配在其他回退段上,以提高资源利用率。 创建回退段时可同时设定其存储参数,回退段至少要包括两个区间(MINEXTENTS),回退段的区间总数受到回退段存储参数MAXEXTENTS的限制。 一个事务的回退信息按顺序在指定的回退段中写入。创建多少个回退段及给每个回退段分配多少区间,要考虑可能出现的最大并发事务数,每个回退段所能同时服务的事务数。,北京邮电大学软件学院 郭文明 20
42、03.06,数据库设计与开发讲义,3.2.4 ORACLE事务控制-回退段,事务的执行过程(采用日志和回退段双重记录事务活动):,进入回退段,写入回退信息,从数据段读入缓冲区,SQL处理,记载日志文件,提交,写更改结果到磁盘,回退,写回退信息到磁盘,事务第一条更新语句,事务结束,N,Y,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.5 ORACLE事务控制-语句,ORACLE事务控制语句: COMMIT WORK;清除本事务的全部保留点,清除为执行事务建立的封锁机制,结束本事务,提交数据. SAVEPOINT 保留点名;保留点是一事务范围内的中间标志,经常用于将长
43、事务划分为短小的部分,保留点可标志在长事务的任何点,允许回退该点之后的工作.保留点主要作为一种调试手段使用.在一个事务中如果用相同的保留点名创建第二个保留点,则前一个保留点被删除掉,每个事务最大的活动保留点由初始化参数文件中的参数SAVEPOINTS设定,极限值为255.,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.5 ORACLE事务控制-语句,ROLLBACK WORK TO SAVEPOINT 保留点名;清除本事务的全部保留点,清除为执行事务建立的封锁机制,结束本事务,回退数据.数据定义语句CREATE、DROP总引发提交,系统正常关闭时,未提交事务将隐式
44、提交,一个进程或例程非正常终止,未提交事务将隐式回退。 SET TRANSACTION READ ONLY READ WRITE USE ROLLBACK SEGMENT 回退段名;设置事务是对事务的一种控制,建立当前事务为只读事务或读写事务,控制事务使用指定的回退段空间。只读事务不生成回退信息,所以不必分配回退段.缺省状态下事务为读写事务。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.6 ORACLE事务控制-数据锁,ORACLE提供了各种类型的封锁机制保证并发操作时数据的一致,对数据库对象的封锁由系统自动完成。数据库应用设计者可以干预自动封锁过程以提高整体效
45、率. ORACLE主要封锁类型有: 数据锁: 目的是保护数据,用于封锁表和表中的某些行; 字典锁: 目的是保护数据库对象的结构,用于表对象的定义; 内部锁: 用于保护数据库的内部结构,如文件等. 数据锁有两种级别的封锁方式: 表封锁:封锁表中的所有行,数据并行度低. 行封锁:行级封锁在对应表上加字典锁.,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.6 ORACLE事务控制-数据锁,ORACLE表上的数据锁类型有: RS:行共享,用于让事务封锁表中的部分行,以便于数据修改,但在建立封锁时并不立即修改数据.当事务在一表持有行共享锁时,允许其他事务并行查询、插入、修改
46、、删除。 RX:行专有,事务可对表中部分行建立专有锁,使事务可以在以后的操作中多次修改这些行。具有行专有锁的表允许其他事务并行查询、插入、修改、删除。 S:共享,共享锁将阻止其他事务修改表中的内容,具有共享锁的表拒绝其他事务插入、修改、删除。 SRX:共享行专有,每个表上的共享行专有锁只能由一个事务建立,有这种类型锁的表只能允许其他事务查询。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.6 ORACLE事务控制-数据锁,X:专有,事务在表上建立专有锁之后,可以独占此表进行写入操作。 ORACLE中的SELECT不用任何数据锁阻塞其他操作,也称无阻塞查询。INSE
47、RT、UPDATE、DELETE引发数据封锁,事务所申请的全部数据锁在事务提交或回退时一起释放,表上的数据锁也可以通过显式语句完成(如下页表)。 表上的数据锁在事务执行过程中可能发生变化,如事务为执行带UPDATE子句的SELECT语句,需在选中行上建立行共享锁,如果稍后事务决定修改其中的某些行,则这些行上的行共享锁将自动转换为行专有锁。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.6 ORACLE事务控制-数据锁,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,3.2.6 ORACLE事务控制-数据锁,数据库设计者应该利用各种方法减少数据对象的封锁时间,以提高系统并发能力:在事务中尽可能晚地发出封锁申请;在备份的数据库对象上操作以减少封锁时间;利用索引减少封锁时间,查询操作可以根本不访问索引关联的表,而直接给出查询结果。 数据库设计者应该按照约定顺序封锁表减少出现死锁的可能性,以提高系统并发能力。,北京邮电大学软件学院 郭文明 2003.06,数据库设计与开发讲义,