一,锁


为了防止用户在同一时间并发地访问和修改资源,ORACLE使用不同类型的锁控制对数据的并发访问,以防止用户之间出现破坏性的交互操作
,oracle 为处理事务自动锁定资源。


  锁在SQL语句开始它们与数据的相互作用时获得,并在事务的整个过程中有效


  oracle9i使用两种锁模式:
  .独占模式(排他):不允许其他任何并发会话以任何方式共享锁定的资源,修改数据时需要这种锁。
  .共享模式:允许对同一块数据的并发读访问。在更改数据时,上升为独占模式



一)行级锁
      insert    update   delete   隐式加行锁(排他)
      select ... for  update  显示加行锁(共享)


      select ...for update 用于显示锁定将要更新的数据行,防止其他用户在更新之前操作此行
                如:select * from emp where deptno=30  for  update
                    update   emp set ename='Joke' where  empno=7499;
  
            在锁释放之前,其他用户不可以对锁定的数据行进行(修改,删除)操作,查询可以
  
      假如有其他用户要锁定同一资源:可以使用wait 子句对锁的等待时间控制
        如:  在另一用户中:select * from emp where deptno=30  for  update  wait  2  (等待2秒 )
      如2秒钟还未释放资源,系统将会给出提示信息


  
  
二)表级锁


    共享模式(in share mode)
    共享更新模式(in share update mode)
    排他锁模式


    锁定表的通用语法:


    lock  table  表名  in  <share  or  share  update  or  exclusive  mode>;


    1) 共享模式
       不允许其他用户插入,更新和删除行,多个用户可以同时在同一表上设置共享锁,这样设置锁的多个用户都只能执行查询  
    
           lock  table emp  in  share  mode;


    2)共享更新模式(in share update mode)
       允许多个用户同时锁定表的不同行, 允许其他用户进行DML(insert update delete select)操作 , 除了已锁定的行            

      如: lock  table emp  in  share update  mode;
                      select *  from  emp  where deptno=30  for update        //锁定的行
        其他用户不能delete ,update 部门30的雇员信息
          
      其他用户可以查看锁定的行:   select *  from  emp  where deptno=30  


    3)排他锁模式(限制性强)
       不允许其他用户插入,更新和删除行, 允许查看数据,但只有一个用户可以在表中放置排他锁
        
           lock   table  emp  in  exclusive mode;
    
三) 死锁


    如:USERA: lock table scott.emp  in  share  mode;    
        USERB: lock table scott.emp  in   share  mode ;
      
       USERA:  update  scott.emp set ename='Smith'  where empno=7369;
       USERB:  update  scott.emp set job='CLERK' where   empno=7521;
       发生死锁


二,表分区


    分区的类型:
     1),范围分区: 分区基于某一特定列或一组列的值的范围
     2),散列分区:数据基于hash 函数进行分区
     3),复合分区:首先基于范围分区,然后使用HASH函数进一步划分为子分区
     4), 列表分区:通过在每个分区的描述中指定分区键的离散值列表,
                   允许按自然方式对无序和不相关的数据集进行分组和组织


  一)范围分区
  
  1)  创建分区表(一列)


       1,创建分区表(一列分区键empno)
         create table emp1(
         empno  number(4),
         ename  varchar2(10),
         job   varchar2(9),
         mgr   number(4),
         hiredate date,
         sal  number(7,2),
         comm  number(7,2),
         deptno  number(2))
         partition  by  range(empno)
         (partition  p1   values  less than  (7566),
          partition  p2   values  less than  (7900),
          partition  p3   values  less than  (9999))
      
      2,插入数据
         insert into emp1 select * from scott.emp;


      3,显示分区数据
        select * from  emp1 partition(p1); --分区键empno,小于7566的empno插入到p1分区
        select * from  emp1 partition(p2);
        select * from  emp1 partition(p3);


      4,数据字典
        col table_name for a15;
        col partition_name for a15;
        select table_name,partition_name from user_tab_partitions;


   2)创建分区表(两列)
      1, 创建分区表(两列deptno,empno)
         create table emp2(
         empno  number(4),
         ename  varchar2(10),
         job   varchar2(9),
         mgr   number(4),
         hiredate date,
         sal  number(7,2),
         comm  number(7,2),
         deptno  number(2))
             partition  by  range(deptno,empno)
            (partition  om1   values  less than  (20,7566), --分区边界的左部分优先,当empno<7566时,deptno=20的记录也将被插入
             partition  om2   values  less than  (30,7900),
             partition  om3   values  less than  (maxvalue,maxvalue))


      2, 插入数据
        insert into emp2  select * from emp;
      3, 显示分区数据
         select * from  emp2 partition(om1);
         select * from  emp2 partition(om2);
         select * from  emp2 partition(om3);


   3) 按日期类型分区
        create table emp3(
        empno  number(4),
        ename  varchar2(10),
        job   varchar2(9),
        mgr   number(4),
        hiredate date,
        sal  number(7,2),
        comm  number(7,2),
        deptno  number(2))
        partition  by  range(hiredate)
        (partition  om1   values  less than  (to_date('1980-12-31','yyyy-mm-dd')),
         partition  om2   values  less than  (to_date('1981-12-31','yyyy-mm-dd')),
         partition  om3   values  less than  (to_date('1982-12-31','yyyy-mm-dd')))  
      
    二)散列分区  
       使用hash 函数将数据划分到分区中
        create table dept1(deptno  number(2),
                    dname   varchar2(14),
                    loc  varchar2(13))
                    partition  by  hash(deptno)
                    (partition p1,partition p2);
        insert into  dept1  select * from scott.dept;


    三)复合分区
        create table salgrade1(grade number,losal number,hisal number)
        partition by range(grade)
        subpartition  by hash(losal,hisal)
              (
              partition p1 values  less than (3)
                 (subpartition  sp1,subpartition sp2),
              partition p2  values  less than (6)
                 (subpartition  sp3,subpartition sp4)
             )


        insert into  salgrade1  select * from   scott.salgrade;

            select * from salgrade1 partition(p1);
            select * from salgrade1 subpartition(sp1);
            select * from salgrade1 subpartition(sp2);


   四)列表分区


     create table  emp4
     (empno  number,
      ename  varchar2(10),
      deptno  number)
      partition  by  list(deptno)
      (
        partition  p1  values(10,20),
        partition  p2  values(30)
      )


     insert into emp4 select empno,ename,deptno from scott.emp;
     select * from emp4 partition(p1);


三,维护分区
    
      --表emp1在其用户所在的表空间中,创建用户时指定,没指定默认为系统表空间
         1)在system用户中授权:
          grant create tablespace to scott;
         2)登录到scott用户
          connect scott/tiger;    --假设在服务器端,客户端要加连接字符串
         3)创建表空间test,该表空间包含一个数据文件,大小是5M
          create tablespace  test datafile        
                       'd:\ora1.dbf'  size 5m;


     1,移动分区
        
        alter table  emp1
                     move  partition p1  tablespace  test;--将分区移动到表空间test
     2,添加分区
         alter table emp3
                     add   partition om4  values less than(to_date('1984-12-31','yyyy-mm-dd'));
              
     3,删除分区
         alter table emp3
                     drop  partition om4;


     4,结合分区--用于散列分区
         使用散列方法分区的表中,可以将某个分区的内容分发到由hash函数确定的一个或多个分区中,然后清除选定的分区
          alter  table dept1  coalesce  partition;


     5,截断分区
           删除分区的数据(不能回滚)
         alter table  emp3   truncate  partition  om3;
         delete from emp3 partition(om1)  //可以回滚


     6, 拆分分区
                原来的分区p2不存在了
                --p21将包括:7566到7700的记录
                --p22将包括:7701到7900的记录
              alter table  emp1  split  partition  p2 at(7700)  
              into(partition  p21,partition  p22);


     7,合并分区
        合并范围分区表中的相邻两个分区的内容,产生新的分区p2,原来的分区p21,p22不存在了
        alter table emp1  merge partitions  p21,p22  into  partition p2;                                            
          
     8,交换表分区
       非分区表的数据和已分区表的某个分区数据进行交换
       要求:非分区表的结构要和已分区表相同
       如:
       1,建立分区表
            create table   Pdept(deptno  number(2),
                    dname   varchar2(14),
                    loc  varchar2(13))
                     partition  by  range(deptno)
                     (partition p1  values less than (20)  tablespace test,    --指定分区所在的表空间
                      partition p2  values less than (maxvalue)  tablespace test);
          
       2,插入(分区表)数据
            insert into  Pdept  select * from dept;


       3,建立非分区表
            create table Sdept as select * from  dept where 1=2;      


       4,插入(非分区表)数据
            insert into  Sdept values(60,'MyDept','MyLoc');


       5,交换分区
           alter table Pdept exchange partition  p2 with  table  Sdept;

posted on 2007-06-05 16:25  思净  阅读(400)  评论(0编辑  收藏  举报