关于ORACLE MYSQL在非前缀分区索引上分区剪裁的比较

ORACLE:
CREATE TABLE testpur (i NUMBER, j NUMBER , f varchar2(20))
     PARTITION BY RANGE(i)
        (PARTITION p1 VALUES LESS THAN (10),
         PARTITION p2 VALUES LESS THAN (20),
         PARTITION p2 VALUES LESS THAN (30),
         PARTITION p2 VALUES LESS THAN (40),
         PARTITION p2 VALUES LESS THAN (50));

declare  
   i number(10);
begin 
  for i in 1..1000
  loop
  insert into purge
   values(mod(i,50),i,'gaopeng');
  end loop;
end;

MYSQL:
CREATE TABLE testpur (i int, j int , f varchar(20))
     PARTITION BY RANGE(i)
        (PARTITION p1 VALUES LESS THAN (10),
         PARTITION p2 VALUES LESS THAN (20),
         PARTITION p3 VALUES LESS THAN (30),
         PARTITION p4 VALUES LESS THAN (40),
         PARTITION p5 VALUES LESS THAN (50));
         
delimiter //
create procedure myproc() 
begin 
declare num int; 
set num=1; 
while num <= 1000 do 
  insert into testpur  values(mod(num,50),num,'test'); 
  set num=num+1;
end while;
 end//
         
这样ORACLE和MYSQL同样的建立了相同的分区表,在ORACLE中,即使查询中使用的索引是本地非前缀索引,也就是本LOCAL索引
不包含分区键本身,这种情况下即使使用本索引也不会触发分区剪裁,但是如果谓词中包含分区键,索引分区剪裁的特性能够用到
如上,我们建立本地非前缀分区索引
SQL> create index testpur_l_nopre on testpur(j) local;
Index created
然后查看他的执行计划

explain plan for select * from  testpur where j=10 and i=19;

PLAN_TABLE_OUTPUT
------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
Plan hash value: 717037044

----------------------------------------------------------------------------------------------------------------------
| Id  | Operation                          | Name            | Rows  | Bytes | Cost (%CPU)| Time     | Pstart| Pstop |
----------------------------------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT                   |                 |     1 |    15 |     2   (0)| 00:00:01 |       |       |
|   1 |  PARTITION RANGE SINGLE            |                 |     1 |    15 |     2   (0)| 00:00:01 |     2 |     2 |
|*  2 |   TABLE ACCESS BY LOCAL INDEX ROWID| TESTPUR         |     1 |    15 |     2   (0)| 00:00:01 |     2 |     2 |
|*  3 |    INDEX RANGE SCAN                | TESTPUR_L_NOPRE |     1 |       |     1   (0)| 00:00:01 |     2 |     2 |
----------------------------------------------------------------------------------------------------------------------

PLAN_TABLE_OUTPUT
------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------

   2 - filter("I"=19)
   3 - access("J"=10)

可以看到及时如此索引任然是在分区2中进行的扫描,也就是说特定条件下非前缀分区索引是可以起到前缀索引效果的

然后我们看看MYSQL的表现,MYSQL没有GLOBAL分区索引一说。只有本地分区索引
我们建立索引

create index testpur_l_nopre on testpur(j) ;
查看执行计划
mysql> explain partitions  select * from  testpur where j=10 and i=19;
+----+-------------+---------+------------+------+-----------------+-----------------+---------+-------+------+-------------+
| id | select_type | table   | partitions | type | possible_keys   | key             | key_len | ref   | rows | Extra       |
+----+-------------+---------+------------+------+-----------------+-----------------+---------+-------+------+-------------+
|  1 | SIMPLE      | testpur | p2         | ref  | testpur_l_nopre | testpur_l_nopre | 5       | const |    1 | Using where |

很显然MYSQL也是用了同样技术,这里不仅用到分区剪裁而且使用到了分区索引 testpur_l_nopre。

另外题外话,MYSQL,ORACLE的主键唯一键必须是分区键的一部分,如果分区键是i,j,那么主键唯一键必须是其中一个。
其原因很简单,在ORACLE 9I 10G 编程艺术中有明确说明,如果允许包含非分区键的局部唯一索引,那么其分区特性
将被消耗殆尽,因为这样不得不去每次扫描全部分区来保证其唯一性,只有包含了分区键才能做到事先判断。

时间: 2024-09-24 21:42:46

关于ORACLE MYSQL在非前缀分区索引上分区剪裁的比较的相关文章

索引键的唯一性(4/4):非唯一聚集索引上的唯一和非唯一非聚集索引

原文:索引键的唯一性(4/4):非唯一聚集索引上的唯一和非唯一非聚集索引 在上一篇文章里,我谈了唯一聚集索引上的唯一和非唯一非聚集索引的区别.在这篇文章里,我想谈下非唯一聚集索引上的唯一和非唯一聚集索引的区别.我们都知道,SQL Server内部把非唯一聚集索引当作唯一聚集索引处理的.如果你定义了一个非唯一聚集索引,SQL Server会增加叫做uniquifier到你的索引记录,它导致你聚集索引的导航结构(B树的非叶子层)里,每条索引行都要用到4 bytes的开销. 下列代码再次创建我们的Cu

Oracle Local VS Global分区索引简介

在Oracle中,索引和表一样也可以分区.有两种类型的分区索引,本地分区索引(Local )和全局分区索引(Global). 1.本地索引(Local) 本地分区索引使用 LOCAL关键字创建,其分区边界与表相同(即与每个表分区相关联都有一个索引分区),下面 是一个本地分区索引的例子: create table sales_par partitioned by range (year) ( partition p_2009 values less than (2010) partition p_

Oracle分区(2) 分区索引

可能很多初学者和我一样,一开始以为只要在分区表上创建的索引就是分区索引,其实不然,索引 是否分区和表是否分区没有必然的关系,表分区索引可以分区也可以不分区,甚至表不分区索引也可 以分区(但很少会这么定义),因此分区索引比分区表要复杂的多. 分区索引主要分为本地分区索引和全局分区索引,本地索引又分为前缀索引和非前缀索引,本文主 要探讨它们的区别. 本地分区索引 本地分区索引是指索引的分区键.分区方式和基表的分区方式一模一样,如下图所示: 本地分区索引具有如下基本特征: 1. 本地索引一定是分区索引

Oracle 分区索引

    分区索引(或索引分区)主要是针对分区表而言的.随着数据量的不断增长,普通的堆表需要转换到分区表,其索引呢,则对应的转换到分区索引.分区索引的好处是显而易见的.就是简单地把一个索引分成多个片断,在获取所需数据时,只需要访问更小的索引片断(块)即可实现.同时把分区放在不同的表空间可以提高分区的可用性和可靠性.本文主要描述了分区索引的相关特性并给出演示示例.   1.分区索引的相关概念a.分区索引的几种方式:表被分区而索引未被分区:表未被分区,而索引被分区:表和索引都被分区b.分区索引可以分为

Oracle 分区索引介绍和实例演示_oracle

分区索引(或索引分区)主要是针对分区表而言的.随着数据量的不断增长,普通的堆表需要转换到分区表,其索引呢,则对应的转换到分区索引.分区索引的好处是显而易见的.就是简单地把一个索引分成多个片断,在获取所需数据时,只需要访问更小的索引片断(块)即可实现.同时把分区放在不同的表空间可以提高分区的可用性和可靠性.本文主要描述了分区索引的相关特性并给出演示示例. 1.分区索引的相关概念 a.分区索引的几种方式:表被分区而索引未被分区:表未被分区,而索引被分区:表和索引都被分区 b.分区索引可以分为本地分区

深入oracle分区索引的详解_oracle

表可以按range.hash.list分区,表分区后,其上的索引和普通表上的索引有所不同,oracle对于分区表上的索引分为2类,即局部索引和全局索引,下面分别对这2种索引的特点和局限性做个总结.局部索引local index1.局部索引一定是分区索引,分区键等同于表的分区键,分区数等同于表的分区数,一句话,局部索引的分区机制和表的分区机制一样.2.如果局部索引的索引列以分区键开头,则称为前缀局部索引.3.如果局部索引的列不是以分区键开头,或者不包含分区键列,则称为非前缀索引.4.局部索引只能依

全局分区索引和局部分区索引

最近正在温习ORACLE分区表,下面是关于全局分区索引和局部分区索引,以及前缀局部分区索引和非前缀局部分区索引的概念和需要注意的地方全局分区索引:索引分区不按照表的分区进行,索引的分区可以指向任何表分区局部分区索引:索引分区完成按照表的分区进行前缀局部分区索引:分区键在索引定义的第一列上非前缀局部分区索引:分区键不在索引定义的第一列上,可能根本不包含分区键1.这里先说明下分区修剪,以及前缀局部分区索引和非前缀局部分区索引的关系何为分区修剪?其实这个是分区表的主要功能,表示可以通过分区,ORACL

SQL Server已分区索引的特殊指导原则(3)

一.前言 在MSDN上看到一篇关于SQL Server 表分区的文档:已分区索引的特殊指导原则,如果你对表分区没有实战经验的话是比较难理解文档里面描述的意思.这里我就里面的一些概念进行讲解,方便大家的交流. SQL Server 解读[已分区索引的特殊指导原则](1)- 索引对齐 SQL Server 解读[已分区索引的特殊指导原则](2)- 唯一索引分区 二.解读 [对非聚集索引进行分区] "对唯一的非聚集索引进行分区时,索引键必须包含分区依据列.对非唯一的非聚集索引进行分区时,默认情况下 S

索引键的唯一性(3/4):唯一聚集索引上的唯一和非唯一非聚集索引

原文:索引键的唯一性(3/4):唯一聚集索引上的唯一和非唯一非聚集索引 在上篇文章里,我讨论了唯一和非唯一聚集索引的区别.我们已经知道,SQL Server内部使用4 bytes的uniquifier来保证非唯一聚集索引行唯一.今天我们来看下唯一聚集索引上,唯一和非唯一非聚集索引的区别.当我们在表上定义PRIMARY KEY约束时,SQL Server会为我们创建唯一聚集索引:另外我们可以通过CREATE UNIQUE CLUSTERED INDEX语句在表上创建唯一聚集索引.下面的代码会创建c