【数据库】数据库并发控制的冲突检测,冲突可串行化的调度,保障变乱的特性 ...

打印 上一主题 下一主题

主题 852|帖子 852|积分 2556

冲突可串行化

   ​专栏内容
  

  • 手写数据库toadb
    本专栏主要先容怎样从零开发,开发的步骤,以及开发过程中的涉及的原理,遇到的问题等,让各人能跟上并且可以一起开发,让每个必要的人成为参与者。
    本专栏会定期更新,对应的代码也会定期更新,每个阶段的代码会打上tag,方便阶段学习。
    ​开源贡献
  

  • toadb开源库
  个人主页:我的主页
管理社区:开源数据库
座右铭:天行健,君子以发奋图强;阵势坤,君子以厚德载物.
  
  

前言

随着信息技术的飞速发展,数据已经渗出到各个范畴,成为现代社会最紧张的资产之一。在这个大数据期间,数据库理论在数据管理、存储和处理处罚中发挥着至关紧张的作用。然而,很多读者可能对数据库理论感到狐疑,不知道怎样选择符合的数据库,怎样设计有用的数据库布局,以及怎样处理处罚和管理大量的数据。因此,本专栏旨在为读者提供一套全面、深入的数据库理论指南,资助他们更好地理解和应用数据库技术。
数据库理论是研究怎样有用地管理、存储和检索数据的学科。在现代信息化社会中,数据量呈指数级增长,怎样高效地处理处罚和管理这些数据成为一个紧张的问题。同时,随着云盘算、物联网、大数据等新兴技术的不停发展,数据库理论的紧张性日益凸显。
因此,本专栏的分享希望可以进步各人对数据库理论的熟悉和理解,对于感兴趣的朋侪带来资助。
概述

商用数据库管理系中的调度器通常逼迫执行被称为“冲突可串行化”的条件,它比前一篇博文中分享的可串行化的一般要强,它是基于冲突这一概念。
我们通常执行的很多并发变乱,都会发生冲突,本文就来分享一下突冲的缘故原由,以及怎样检测冲突发生,怎样做到冲突可串行化。
冲突

起首我们先来了解一下冲突是什么?
冲突的概念

冲突,即调度中一对连续的动作,它们满意,如果它们的次序发生互换,那么它们涉及的变乱至少有一个的举动会改变。
冲突的发生条件

一般什么环境下会发生冲突呢?
数据库的操纵可以分为写和读两种,我们看一下两个变乱,分别有一个操纵时,什么环境下为会产生冲突。


  • 当两个变乱对同一数据库元素读时,先后次序互换,并不发生结果的改变,不会冲突;
  • 当两个变乱操纵同一个数据元素时,有一个读,一个写时,先后次序互换,读操纵的变乱的结果就会不一样,这时就会产生冲突;
  • 当两个变乱操纵同一个数据元素时,两个变乱都进行写操纵,先后次序互换,两个变乱的结果都不会一样;
  • 当两个变乱操纵不同数据库元素时,不管是读还是写,次序互换,结果都不会受影响,所以不会产生冲突;
从上面例子可以得到这样一个结论:


  • 不同变乱操纵同一个数据库元素;
  • 操纵中至少有一个是写操纵;
那么我们将一个执行序列进行调度,进行恣意非冲突的可串行化调度,目标是将这一序列转化为可串行化,如果能到达这一点,那么它最初调度是可串行化的调度,因为在做每一个非冲突可串行化调度时,初始状态一样,对数据库的影响在不同序列下是一样的。
冲突可串行化



  • 如果对于并发执行的序列进行一系列相邻动作的非冲突互换,能转换为另一个,这两个调度可以称为冲突等价的。
  • 如果一个冲突调度等价于一个可串行化调度,那么可以称这个调度为冲突可串行化;
当然冲突可串行化是可串行化的充分非必要条件,
优先图检测方法

通过上面的冲突发生条件分析,阐明变乱的语义会影响串行化,但是对于调度器来说,它不会深入到变乱执行的细节,但是调度器能够看来自变乱的读写哀求,以及那些数据元素发生了改变,这样它可以通过数据元组的访问来辨认冲突。
在一个调度执行序列中,可以确定冲突动作对应的变乱的先后次序,怎样变乱先后次序在不同冲突动作上,出现出不同的次序,那么我们认为是冲突不可串行化的。
那这一特点通过优先图就可以表现出来。
  1. T1->T2->T3
复制代码
如果是这样一个图,那么就是冲突可串行化的。
  1. T1->T2->T3
  2. ->T2
复制代码
如果是这样一个图,T2与T3之间存在了一个环,那么就是冲突不可串行化的。
总结

在数据库并发变乱环境下,冲突是不可避免的,通过优先图的方法来检测冲突,使得调度器能够找到一种冲突可串行化的调度方案。
这是一个简单的C语言程序,它利用了状态模式来输出"Hello, world!":
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. // 定义状态结构体
  4. typedef struct State State;
  5. struct State {
  6.     void (*printMessage)(void);
  7. };
  8. // 定义转换函数
  9. void printHello(void) {
  10.     printf("Hello, world!\n");
  11. }
  12. // 定义初始状态
  13. State initialState = { .printMessage = printHello };
  14. // 定义状态转换函数
  15. void transition(State *state) {
  16.     switch (*state) {
  17.         case 'H':
  18.             (*state).printMessage = printHello;
  19.             break;
  20.         default:
  21.             printf("Invalid state\n");
  22.             break;
  23.     }
  24. }
  25. int main() {
  26.     State state = initialState;
  27.     transition(&state);
  28.     return 0;
  29. }
复制代码
这个程序定义了一个状态布局体,此中有一个函数指针用于指向打印消息的函数。然后定义了一个初始状态,该状态中的函数指针指向printHello函数。transition函数担当一个指向状态的指针,并根据当前状态来改变它指向的函数。在main函数中,我们起首设置初始状态,然后调用transition函数来改变状态。
结尾

   非常感谢各人的支持,在浏览的同时别忘了留下您宝贵的评论,如果觉得值得鼓励,请点赞,收藏,我会更加积极!
  作者邮箱:study@senllang.onaliyun.com
如有错误或者疏漏接待指出,互相学习。

免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?立即注册

x
回复

使用道具 举报

0 个回复

倒序浏览

快速回复

您需要登录后才可以回帖 登录 or 立即注册

本版积分规则

小秦哥

金牌会员
这个人很懒什么都没写!

标签云

快速回复 返回顶部 返回列表