zoukankan      html  css  js  c++  java
  • Oracle 分区表-Range分区

    原文:http://www.tuicool.com/articles/MzeM7r

    一、什么是分区表

           Oracle提供了分区技术以支持VLDB(Very Large DataBase)。分区表通过对分区列的判断,把分区列不同的记录,放到不同的分区中。分区完全对应用透明。

           Oracle的分区表可以包括多个分区, 每个分区都是一个独立的段( SEGMENT),可以存放到不同的表空间中 。查询时可以通过查询表来访问各个分区中的数据,也可以通过在查询时直接指定分区的方法来进行查询。

     二、什么时候用分区表

    When to Partition a Table 什么时候需要分区表,官网的 2 个建议如下:

    (1)Tables greater than 2GB should always be considered for partitioning.

    (2)Tables containing historical data, in which new data is added into the newest partition. A typical example is a historical table where only the current month's data is updatable and the other 11 months are read only.

    三、分区表优点

           (1)由于将数据分散到各个分区中,减少了数据损坏的可能性;

           (2)可以对单独的分区进行备份和恢复;

           (3)可以将分区映射到不同的物理磁盘上,来分散IO;

           (4)提高可管理性、可用性和性能。

    四、分区表类型

           (1)范围分区(range)——我们这篇博文的内容;

           (2)哈希分区(hash);

           (3)列表分区(list);

           (4)范围-哈希复合分区(range-hash);

           (5)范围-列表复合分区(range-list)。

    五、Range 分区

    Range分区是应用范围比较广的表分区方式,它是以列的值的范围来做为分区的划分条件,将记录存放到列值所在的range分区中。

           如按照时间划分,2010年1月的数据放到a分区,2月的数据放到b分区,在创建的时候,需要指定基于的列,以及分区的范围值。

           在按时间分区时, 如果某些记录暂无法预测范围,可以创建 maxvalue 分区,所有不在指定范围内的记录都会被存储到 maxvalue 所在分区中。

    六、Range分区实例说明

    例子:创建一张表,表有两个字段(ID、TIME),我们完成对TIME列的范围分区,即将1-12月创建成对应的12个分区表,对分区表及分区表数据进行增删查改操作。

    创建分区表:

    创建表同时完成对表进行分区(按月份分区)

     
    /*创建分区表*/
    create table pdba (id number, time date) partition by range (time)
    (
      partition p1 values less than (to_date('2013-02-1', 'yyyy-mm-dd')),
      partition p2 values less than (to_date('2013-03-1', 'yyyy-mm-dd')),
      partition p3 values less than (to_date('2013-04-1', 'yyyy-mm-dd')),
      partition p4 values less than (to_date('2013-05-1', 'yyyy-mm-dd')),
      partition p5 values less than (to_date('2013-06-1', 'yyyy-mm-dd')),
      partition p6 values less than (to_date('2013-07-1', 'yyyy-mm-dd')),
      partition p7 values less than (to_date('2013-08-1', 'yyyy-mm-dd')),
      partition p8 values less than (to_date('2013-09-1', 'yyyy-mm-dd')),
      partition p9 values less than (to_date('2013-10-1', 'yyyy-mm-dd')),
      partition p10 values less than (to_date('2013-11-1', 'yyyy-mm-dd')),
      partition p11 values less than (to_date('2013-12-1', 'yyyy-mm-dd')),
      partition p12 values less than (to_date('2014-01-1', 'yyyy-mm-dd'))
      --partition p13 values less than (maxvalue)    --不建议使用
    )

    查询所有分区表,验证分区表是否创建成功。

    select * from ALL_TAB_PARTITIONS a --不能加任何where条件

    结果如下图:

    添加数据:

    为了测试效果,我们添加120万条数据,每月添加10万条数据:

     
    /*添加数据*/
    declare   
    begin  
              for n in 1..100000 LOOP  
              -- insert into sale_data select * from sale_data;
                insert into pdba VALUES(1,to_date('2013-01-05','yyyy-mm-dd'));
                insert into pdba VALUES(2,to_date('2013-02-05','yyyy-mm-dd'));
                insert into pdba VALUES(3,to_date('2013-03-05','yyyy-mm-dd'));
                insert into pdba VALUES(4,to_date('2013-04-05','yyyy-mm-dd'));
                insert into pdba VALUES(5,to_date('2013-05-05','yyyy-mm-dd'));
                insert into pdba VALUES(6,to_date('2013-06-05','yyyy-mm-dd'));
                insert into pdba VALUES(7,to_date('2013-07-05','yyyy-mm-dd'));
                insert into pdba VALUES(8,to_date('2013-08-05','yyyy-mm-dd'));
                insert into pdba VALUES(9,to_date('2013-09-05','yyyy-mm-dd'));
                insert into pdba VALUES(10,to_date('2013-10-05','yyyy-mm-dd'));
                insert into pdba VALUES(11,to_date('2013-11-05','yyyy-mm-dd'));
                insert into pdba VALUES(12,to_date('2013-12-05','yyyy-mm-dd'));
         end loop;   
    end;

    测试数据是否添加正确:

    先查看物理表记录:

    /*验证*/
    select count(*) from pdba
    结果如下图:
     

    再随机查看分区表,数据, 比如我们查看12月份的分区表数据,理论应该是10W条。

    /*分区表查询*/
    select count(*) from pdba partition(p12)  --一月份
     
           

    至此我们创建、验证、并向表中添加数据 完成。

     

    查询分区表:

    /*分区表查询*/
    select * from pdba partition(p12)  --十二月份

    删除分区表:

    ( 数据也会被删除 )

    /*删除分区表*/
    ALTER TABLE pdba DROP PARTITION P12;

    当我们再次查询十二月份的分区表时:
    /*分区表查询*/
    select * from pdba partition(p12)  --十二月份
     
    结果如下:

    而我们物理表中数据也会减少10w条。

    select count(*) from pdba

    结果如下:
     

    增加分区表:

    现在的物理表只有1到11月份的分区表,那我们再次添加12月份的分区表并再次添加10w条数据

    /*增加分区表*/
    ALTER TABLE pdba ADD PARTITION P12 VALUES LESS THAN(TO_DATE('2014-01-01','YYYY-MM-DD'));


    添加数据:

    /*添加数据*/
    declare   
    begin  
              for n in 1..100000 LOOP  
        insert into pdba VALUES(12,to_date('2013-12-05','yyyy-mm-dd'));
         	  end loop;   
    end;


    再次查询十二月份的分区表验证操作是否成功

    /*分区表查询*/
    select count(*) from pdba partition(p12)  --十二月份


    结果如图:

     

    合并分区表:

    例子:将11月和12月的分区表合并在一起。

    /*合并分区表*/
    ALTER TABLE pdba MERGE PARTITIONS p11, p12 INTO PARTITION p13


    分区表合并后,原分区表空间被释放,原数据均转移到新的表空间下。

    现在查询新的分区表,数据应该为20w条。

    select count(*) from pdba partition(p13)


    结果如图:

    分割分区表:

     

    例子:将p13分区表分割成p11和p12分区表,即将11月和12月数据重新分割开。

    /*一个分区表分割成两个分区表*/
    alter table pdba split Partition p13 at (to_date('2013-12-01','yyyy-mm-dd')) into (Partition p11,Partition p12);


    过程和合并分区表下相反。

    现在p11和p12表空间和数据重新恢复和添加。

    11月和12月各10w条数据

    更改分区表名:

    --更改分区表名 
    alter table pdba rename Partition p11 to p22;

    增删查改分区表的数据:

    操作与物理表几乎相同, 只是操作分区表时在分区表前加入 物理表名称即可。具体如下图:

     
    --查询分区表数据
    select DISTINCT * from pdba partition(p12)  
    --修改分区表数据
    update pdba partition(p12) p set p.time = to_date('2013-12-08','yyyy-mm-dd'); 
    --增加分区表数据
    insert into pdba partition(p12) p VALUES(1,to_date('2013-12-29','yyyy-mm-dd'));
    --删除分区表数据
    delete from pdba partition(p12) t where t.id = 1

    七、附录:

    显示分区表信息 

    显示数据库所有分区表的信息:DBA_PART_TABLES 

    显示当前用户可访问的所有分区表信息:ALL_PART_TABLES 

    显示当前用户所有分区表的信息:USER_PART_TABLES 

    显示表分区信息 显示数据库所有分区表的详细分区信息:DBA_TAB_PARTITIONS 

    显示当前用户可访问的所有分区表的详细分区信息:ALL_TAB_PARTITIONS 

    显示当前用户所有分区表的详细分区信息:USER_TAB_PARTITIONS 

    显示子分区信息 显示数据库所有组合分区表的子分区信息:DBA_TAB_SUBPARTITIONS 

    显示当前用户可访问的所有组合分区表的子分区信息:ALL_TAB_SUBPARTITIONS 

    显示当前用户所有组合分区表的子分区信息:USER_TAB_SUBPARTITIONS 

    显示分区列 显示数据库所有分区表的分区列信息:DBA_PART_KEY_COLUMNS 

    显示当前用户可访问的所有分区表的分区列信息:ALL_PART_KEY_COLUMNS 

    显示当前用户所有分区表的分区列信息:USER_PART_KEY_COLUMNS 

    显示子分区列 显示数据库所有分区表的子分区列信息:DBA_SUBPART_KEY_COLUMNS 

    显示当前用户可访问的所有分区表的子分区列信息:ALL_SUBPART_KEY_COLUMNS 

    显示当前用户所有分区表的子分区列信息:USER_SUBPART_KEY_COLUMNS 

    Range分区表基本操作如上,高级操作,如分区表下在分区,建立视图等,未完待续。 

  • 相关阅读:
    【基础算法】- 全排列
    【基础算法】- 2分查找
    区块链培训
    Static Binding (Early Binding) vs Dynamic Binding (Late Binding)
    test
    No data is deployed on the contract address!
    "throw" is deprecated in favour of "revert()", "require()" and "assert()".
    Variable is declared as a storage pointer. Use an explicit "storage" keyword to silence this warning.
    京都行
    Failed to write genesis block: database already contains an incompatible
  • 原文地址:https://www.cnblogs.com/linn/p/4244221.html
Copyright © 2011-2022 走看看