外鍵未加索引和加索引的區別

          主要描述外鍵未加索引和加索引的區別:
           
          首先建相關表:
          create table dept (dept_id number(2), name varchar2(20));   
          alter table dept add (constraint pk_dept primary key (dept_id)); 
           
          --在外鍵上沒有建索引的子表
          CREATE TABLE emp
             (emp_id number(10),
              name varchar2(20) ,
              dept_id number(2) CONSTRAINT fk_emp
                                references dept(dept_id)
                                ON DELETE CASCADE
             );
          alter table emp add (constraint pk_emp primary key (emp_id));  
           
          insert into dept values (10,'ACCOUNTING'); 
          insert into dept values (11,'SALES'); 
          insert into dept values (12,'RESEARCH'); 
          insert into dept values (14,'TT');  
           
          insert into emp values (2001,'Jason',10); 
          insert into emp values (2002,'Mike',11); 
          insert into emp values (2003,'Green',12); 
          insert into emp values (2004,'Grey',10); 
           
          外鍵未加索引情況,實驗如下:
          實驗1、
          Session1:對子表進行插入操作:
          insert into emp values(2005,'dai',14);
           
          session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row share            DEPT                    11         12        503
          DAIMIN            142 Row Exclusive        EMP                     11         12        503
           
          SQL> @c:\showalllock;
                 SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TM        55606          0 Row share                     0          6          0
                 142 TX       720908        503 Exclusive                     0          6          0
                 142 TM        55612          0 Row Exclusive                 0          6          0
          分析:對子表進行插入操作時,此時盡管只是對子表操作,但是需要驗證被插入的記錄中的外鍵值是否在父表中是否存在,不存在,則會報錯;存在的話,則允許插入。此時需要對父表加RS鎖,鎖住外鍵值所對應父表被引用鍵值的行;除了對父表加RS鎖之外,對子表還要加RX鎖和TX鎖。
           
          實驗2、
          Session2:對子表EMP進行更新操作,并且所更新的行在子表中實際不存在或者存在:
          update emp  set name=name  where dept_id=15;
          或者update emp  set name=name  where dept_id=11;
           
          Session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME          SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row Exclusive        EMP                     14         28        499
           
          SQL> @c:\showalllock;
                SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TX       917532        499 Exclusive                     0         87          0
                 142 TM        55612          0 Row Exclusive                0         87          0
          分析:僅對子表中除外鍵以外的值進行更新,此時不需要牽涉到父表,所以此時的更新操作不需要對父表加任何的鎖,只需要對子表加RX鎖和TX鎖。
           
          實驗3、
          Session3:對子表進行刪除操作,并且由刪除條件查詢出來的記錄為空或者不為空時:
          delete from emp where 1=0;
          或者 delete from emp ;
           
          Session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row share            DEPT                    17         28        502
          DAIMIN            142 Row Exclusive        EMP                     17         28        502
           
          SQL> @c:\showalllock;
             SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TM        55606          0 Row share                     0          6          0—DEPT表上的RS
                 142 TX      1114140        502 Exclusive                      0          6          0 --EMP表上的TX
                 142 TM        55612          0 Row Exclusive                 0          6          0 –EMP表上的RX
          注:BLOCK=1 :表示鎖被阻塞;BLOCK=0,表示未阻塞。
          分析:對子表進行刪除操作,也需要對父表加RS鎖,猜想是因為需要驗證被刪除的這些記錄中的外鍵值是否在父表還存在,所以需要在父表中加RS鎖。然后對子表本身需要加RX鎖和TX鎖。
           
          實驗4、
          Session4:更新子表的外鍵列:
          update emp set dept_id= 12 where dept_id=11;
           
          Session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row share            DEPT                    12         17        661
          DAIMIN            142 Row Exclusive        EMP                     12         17        661
           
          SQL> @c:\showalllock;
              SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TM        55606          0 Row share                     0          6          0
                 142 TX       786449         661 Exclusive                     0          6          0
                 142 TM        55612          0 Row Exclusive                 0          6          0
          分析:和實驗2比較,都是對子表進行更新操作,但是該實驗是對外鍵值進行的更新,牽涉到父表,所以需要對父表DEPT加RS鎖,子表EMP本身需要加RX鎖和TX鎖。
           
          實驗5、
          Session5:對父表進行插入操作:
          insert into dept values(15,'daimin');
           
          Session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN   XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row Exclusive        DEPT                   13         36        671
          DAIMIN            142 Row share            EMP                     13         36        671
           
          SQL> @c:\showalllock;
                SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TM        55606          0 Row Exclusive                 0          6          0
                 142 TX       852004         671 Exclusive                     0          3          0
                 142 TM        55612          0 Row share                     0          6          0
          分析:對父表進行插入操作,此時需要對父表DEPT加RX鎖和TX鎖,同時需要對子表EMP加RS鎖。
           
          實驗6、
          Session4:對父表DEPT進行更新操作,并且所更新的行在父表中實際不存在或者不存在:
          update dept set name=name where dept_id=16;
          或者 update dept set name=name where dept_id=12;
           
          Session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row Exclusive        DEPT                    15         18        668
           
          SQL> @c:\showalllock;
                 SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TX       983058        668 Exclusive                     0          6          0
                 142 TM        55606          0 Row Exclusive                 0          6          0
          分析:僅對父表中的記錄進行更新,此時不需要牽涉到子表,所以此時的更新操作不需要對子表加任何的鎖,只需要對父表加RX鎖和TX鎖。
           
           
          實驗7、
          Session7: 對父表DEPT進行刪除操作,并且所更新的行在父表中實際不存在或者實際存在:
          delete from dept where 1=0;
          或者 delete from dept where dept_id=12;
           
          Session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row Exclusive        DEPT                    15         28        671
          DAIMIN            142 Row Exclusive        EMP                     15         28        671
           
          SQL> @c:\showalllock;
               SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TM        55606          0 Row Exclusive                 0          6          0
                 142 TX       983068        671 Exclusive                     0          6          0
                 142 TM        55612          0 Row Exclusive                 0          6          0
          分析:對父表DEPT與子表EMP都加了RS鎖,并且由于是對DEPT父表進行刪除行記錄,所以為父表加了TX鎖。有點疑問:我在創建子表時使用了ON DELETE CASCADE語句,為什么我在刪除父表的記錄時沒有造成子表的相應記錄刪除呢?猜想應該在子表EMP上也應該有TX鎖。
           
          外鍵加索引情況,實驗如下:
          給表EMP的外鍵添加索引如下:
          -- Create/Recreate indexes on the Foreign Key
          create index EMP_DEPT_ID on EMP (DEPT_ID);
           
          實驗1、
          Session1:對子表進行插入操作:
          insert into emp values(2005,'dai',14);
           
          session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row share            DEPT                    19         47        673
          DAIMIN            142 Row Exclusive        EMP                    19         47        673
           
          SQL> @c:\showalllock;
                 SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TM        55606          0 Row share                     0          6          0
                 142 TX      1245231        673 Exclusive                     0          6          0
                 142 TM        55612          0 Row Exclusive                 0          6          0
          分析:與外鍵沒有加索引的情況中的實驗1所加的鎖一樣,沒有區別。
           
          實驗2、
          Session2:對子表EMP進行更新操作,并且所更新的行在子表中實際不存在或者存在:
          update emp  set name=name  where dept_id=15;
          或者update emp  set name=name  where dept_id=11;
           
          Session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row Exclusive        EMP                     13         13        676
           
          SQL> @c:\showalllock;
                 SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TX       851981        676 Exclusive                     0          6          0
                 142 TM        55612          0 Row Exclusive                 0          6          0
          分析:與外鍵沒有加索引的情況中的實驗2所加的鎖一樣,沒有區別。
           
           
          實驗3、
          Session3:對子表進行刪除操作,并且由刪除條件查詢出來的記錄為空或者不為空時:
          delete from emp where 1=0;
          或者 delete from emp ;
           
          Session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row share            DEPT                    17         28        502
          DAIMIN            142 Row Exclusive        EMP                     17         28        502
           
          SQL> @c:\showalllock;
              SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TM        55606          0 Row share                     0          6          0—DEPT表上的RS
                 142 TX      1114140        502 Exclusive                      0          6          0 --EMP表上的TX
                 142 TM        55612          0 Row Exclusive                 0         6          0 –EMP表上的RX
          注:BLOCK=1 :表示鎖被阻塞;BLOCK=0,表示未阻塞。
          分析:與外鍵沒有加索引的情況中的實驗3所加的鎖一樣,沒有區別。
           
          實驗4、
          Session4:更新子表的外鍵列:
          update emp set dept_id= 12 where dept_id=11;
           
          Session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row share            DEPT                    12         17        661
          DAIMIN            142 Row Exclusive        EMP                     12         17        661
           
          SQL> @c:\showalllock;
              SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TM        55606          0 Row share                     0          6          0
                 142 TX       786449         661 Exclusive                     0          6          0
                 142 TM        55612          0 Row Exclusive                 0          6          0
          分析:與外鍵沒有加索引的情況中的實驗4所加的鎖一樣,沒有區別。
           
          實驗5、
          Session5:對父表進行插入操作:
          insert into dept values(15,'daimin');
           
          Session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row Exclusive        DEPT                   13         36        671
          DAIMIN            142 Row share            EMP                     13         36        671
           
          SQL> @c:\showalllock;
                SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TM        55606          0 Row Exclusive                 0          6          0
                 142 TX       852004         671 Exclusive                     0          3          0
                 142 TM        55612          0 Row share                     0          6          0
          分析:與外鍵沒有加索引的情況中的實驗5所加的鎖一樣,沒有區別。
           
          實驗6、
          Session4:對父表DEPT進行更新操作,并且所更新的行在父表中實際不存在或者不存在:
          update dept set name=name where dept_id=16;
          或者 update dept set name=name where dept_id=12;
           
          Session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row Exclusive        DEPT                    15         18        668
           
          SQL> @c:\showalllock;
                 SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TX       983058        668 Exclusive                     0          6          0
                 142 TM        55606          0 Row Exclusive                 0          6          0
          分析:與外鍵沒有加索引的情況中的實驗6所加的鎖一樣,沒有區別。
           
          實驗7
          Session7: 對父表DEPT進行刪除操作,并且所更新的行在父表中實際不存在:
          delete from dept where 1=0;
           
          Session0:此時加鎖的信息都是如下:
           
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row Exclusive        DEPT                    13         38        676
          DAIMIN            142 Row share            EMP                     13         38        676
           
          SQL> @c:\showalllock;
               SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TM        55606          0 Row Exclusive                 0          5          0
                 142 TX       852006        676 Exclusive                     0          5          0
                 142 TM        55612          0 Row share                    0          5          0
          分析:猜測可能是由于在父表中根本沒有查找到記錄,所以就在子表中不需要對子表EMP行進行刪除,所以對子表EMP加的是RS鎖。這里和外鍵沒有加索引的情況中的實驗7所加的鎖一樣有鎖不一樣,在子表中所加的鎖是RS鎖,而不是RX鎖。
           
          實驗8、
          Session7: 對父表DEPT進行刪除操作,并且所更新的行在父表中實際存在:
           delete from dept where dept_id=12;
           
          Session0:此時加鎖的信息都是如下:
          SQL> @c:\showlock;
          O_NAME            SID LOCK_TYPE            OBJECT_NAME         XIDUSN    XIDSLOT     XIDSQN
          ---------- ---------- -------------------- --------------- ---------- ---------- ----------
          DAIMIN            142 Row Exclusive        DEPT                    15         28        671
          DAIMIN            142 Row Exclusive        EMP                     15         28        671
           
          SQL> @c:\showalllock;
               SID TYPE        ID1        ID2 LOCK_TYPE               REQUEST      CTIME      BLOCK
          ---------- ---- ---------- ---------- -------------------- ---------- ---------- ----------
                 142 TM        55606          0 Row Exclusive                 0          6          0
                 142 TX       983068        671 Exclusive                     0          6          0
                 142 TM        55612          0 Row Exclusive                 0          6          0
          分析:與外鍵沒有加索引的情況中的實驗7所加的鎖一樣,沒有區別。

          posted on 2008-06-18 15:19 球球 閱讀(606) 評論(0)  編輯  收藏 所屬分類: Oracle

          <2025年6月>
          25262728293031
          1234567
          891011121314
          15161718192021
          22232425262728
          293012345

          導航

          統計

          留言簿(1)

          文章分類(19)

          文章檔案(19)

          積分與排名

          最新隨筆

          最新評論

          主站蜘蛛池模板: 辽宁省| 信宜市| 信丰县| 庄浪县| 辽宁省| 罗平县| 巩义市| 临江市| 鹤峰县| 河间市| 常山县| 团风县| 梅州市| 延边| 平山县| 海门市| 鄂州市| 大悟县| 会理县| 汕头市| 当雄县| 石屏县| 桂平市| 松溪县| 屯留县| 游戏| 太白县| 滕州市| 石景山区| 乌兰察布市| 怀安县| 越西县| 如东县| 潮安县| 工布江达县| 侯马市| 平和县| 华阴市| 和田市| 阆中市| 岐山县|