Oracle与KingbaseES的NULL在索引使用上的区别
NULL值是关系型数据库系统中比较特殊的一种值,通常称为UNKNOWN或空值,即是未知的,不确定的。由于NULL存在着无数的可能,因此NULL值也不等于NULL值。
Oracle在创建索引时,不会存储NULL值,而KingbaseES在创建索引时则会存储NULL值.在查询时,如使用Column is null这样的条件查询,Oracle不会使用索引而KingbaseES则会使用索引。
oracle
SQL> create table tb1(id int);
Table created.
SQL> insert into tb1 select rownum from dba_objects;
86988 rows created.
SQL> commit;
Commit complete.
SQL> create index i_tb1 on tb1(id);
Index created.
SQL> insert into tb1 values(null);
1 row created.
SQL> commit;
Commit complete.
SQL> exec dbms_stats.gather_table_stats('TEST','TB1',cascade=>true); --这里收集统计信息
PL/SQL procedure successfully completed.
SQL> select count(*) from tb1;
COUNT(*)
----------
86989
SQL> select index_name,index_type,num_rows,status,distinct_keys from dba_indexes where table_name='TB1';
INDEX_NAME INDEX_TYPE NUM_ROWS STATUS DISTINCT_KEYS
---------- ---------- ---------- ---------------- -------------
I_TB1 NORMAL 86988 VALID 86988
这里可以看到统计信息收集后,索引统计信息中只有86988行记录,而表的数据是86989行。可以看出索引并没有存储null值,所以少了1行记录。
SQL> set autotrace on explain;
SQL> select * from tb1 where id is null;
ID
----------
Execution Plan
----------------------------------------------------------
Plan hash value: 3226679318
--------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
--------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 5 | 68 (0)| 00:00:01 |
|* 1 | TABLE ACCESS FULL| TB1 | 1 | 5 | 68 (0)| 00:00:01 |
--------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
1 - filter("ID" IS NULL)
SQL> select * from tb1 where id = 9999;
ID
----------
9999
Execution Plan
----------------------------------------------------------
Plan hash value: 3913851163
--------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
--------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 5 | 1 (0)| 00:00:01 |
|* 1 | INDEX RANGE SCAN| I_TB1 | 1 | 5 | 1 (0)| 00:00:01 |
--------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
1 - access("ID"=9999)
查询普通数据时能够走索引扫描,当查询条件为is null时走的是全表扫描。
KingbaseES
test=# create table tb1(id int);
CREATE TABLE
test=# insert into tb1 select generate_series(1,100000);
INSERT 0 100000
test=# insert into tb1 values (null);
INSERT 0 1
test=# create index i_tb1 on tb1(id);
CREATE INDEX
test=# analyze tb1;
ANALYZE
test=# select relname,reltuples from sys_class where relname ~ 'tb1';
relname | reltuples
---------+-----------
tb1 | 100001
i_tb1 | 100001
(2 行记录)
可以看出表和索引记录是一样的,即索引是存了null的记录。
test=# explain analyze select * from tb1 where id is null;
QUERY PLAN
----------------------------------------------------------------------------------------------------------------
Index Only Scan using i_tb1 on tb1 (cost=0.29..4.31 rows=1 width=4) (actual time=0.048..0.061 rows=1 loops=1)
Index Cond: (id IS NULL)
Heap Fetches: 1
Planning Time: 0.204 ms
Execution Time: 0.134 ms
(5 行记录)
查询条件为is null时KingbaseES是可以走索引扫描的
Oracle与KingbaseES的NULL在索引使用上的区别的更多相关文章
- oracle避免在索引列上使用IS NULL和IS NOT NULL
避免在索引中使用任何可以为空的列,ORACLE将无法使用该索引 .对于单列索引,如果列包含空值,索引中将不存在此记录. 对于复合索引,如果每个列都为空,索引中同样不存在此记录. 如果至少有一个列不为空 ...
- oracle数据库什么情况下创建索引比较好
索引就好象一本字典的目录.凭借字典的目录,我们可以非常迅速的找到我们所需要的条目.数据库也是如此.凭借Oracle数据库的索引,相关语句可以迅速的定位记录的位置,而不必去定位整个表. 虽 然说,在表中 ...
- Oracle学习总结_day06_视图&序列&索引
本文为博主辛苦总结,希望自己以后返回来看的时候理解更深刻,也希望可以起到帮助初学者的作用. 转载请注明 出自 : luogg的博客园 谢谢配合! day 06 视图,索引,序列 视图 什么是视图: 视 ...
- Oracle 表的访问方式(2)-----索引扫描
索引扫描(Index scan) 我们先通过index查找到数据对应的rowid值(对于非唯一索引可能返回多个rowid值),然后根据rowid直接从表中得到具体的数据,这种查找方式称为索引扫描或索引 ...
- Oracle性能分析7:创建索引
在创建索引时,我们往往希望可以预估索引大小,以评估对现有project环境的影响,我们也希望创建索引的过程可以最小化的影响我们正在执行的project环境,并能查看索引的状况. 预估索引大小 预估索引 ...
- SQL Server、Oracle和MySQL判断NULL的方法
SQL Server.Oracle和MySQL判断NULL的方法 本文讲述SQL Server.Oracle.MySQL查出值为NULL的替换. 在SQL Server Oracle MySQL当数据 ...
- oracle的约束隐式创建索引和先索引后约束的区别
oracle的约束隐式创建索引和先索引后约束的区别 两种情况:1.对于创建约束时隐式创建的索引,在做删除操作的时候: 9i~11g都会连带删除该索引 2.对于先创建索引,再创建约束(使用到此索引)这种 ...
- sqlserver、oracle数据库排序空值null问题解决办法
转:https://www.cnblogs.com/pacer/archive/2010/03/02/1676371.html [sqlserver]: sqlserver 认为 null 最小. 升 ...
- oracle 如何预估将要创建的索引的大小
一.1 oracle 如何预估将要创建的索引的大小 oracle 提供了2种可以预估将要创建的索引大小的办法: ① 利用包 Dbms_space.create_index_cost 直接得到 ② ...
随机推荐
- 集成学习——GBDT(手推公式)
- 一图读懂k8s informer client-go
概述 为什么要有k8s informer 我们都知道可以使用k8s的Clientset来获取所有的原生资源对象,那么怎么能持续的获取集群的所有资源对象,或监听集群的资源对象数据的变化呢?这里不需要轮询 ...
- bat实现删除BCUnrar.dll实现无限使用
删除项目:计算机\HKEY_CURRENT_USER\Software\Scooter Software\Beyond Compare 4下的CacheId 项可以实现Beyond Compare 4 ...
- NC15052 求最值
NC15052 求最值 题目 题目描述 给你一个长为 \(n\) 的序列 \(a\) 定义 \(f(i,j)=(i-j)^2+g(i,j)^2\) \(g\) 是这样的一个函数 求最小的 \(f(i, ...
- LinkedList集合和Vector集合
LinkedList集合数据存储的结构是链表结构.方便元素添加.删除的集合.实际开发中对一个集合元素的添加与删除经常涉及到首尾操作,而LinkedList提供了大量首尾操作的方法 LinkedList ...
- 【docker专栏2】CentOS操作系统安装DockerCE
目录 一.前置要求 二.更新软件源信息 三.安装 Docker-CE 四.卸载Docker CE 为大家介绍在CentOS操作系统中安装docker的过程,linux其他发行版本安装docker方法可 ...
- OneOS家族,LITE版小兄弟诞生了!
号外,号外!OneOS-Lite诞生啦!前有大哥OneOS,以及一众优秀的RTOS,正所谓珠玉在前,我很难啊.但我可不能怂,大哥叫小O,我就叫小L,站在大哥的肩上,小小L也有发光发热的机会. 小L代码 ...
- idea 内置tomcat jersey 跨服务器 上传文件报400错误
报错内容 com.sun.jersey.api.client.UniformInterfaceException: PUT http://.jpg returned a response status ...
- 10分钟带你进入Swagger的世界,快来看一看吧
什么是Swagger? 如下引用swagger官方的解释 Swagger is a powerful yet easy-to-use suite of API developer tools for ...
- Re:用webpack从零开始的vue-cli搭建'生活'
有了vue-cli的帮助,我们创建vue的项目非常的方便,使用vue create然后选择些需要的配置项就能自动帮我们创建配置好的webpack项目脚手架了,实在是'居家旅行'必备良药.这次借着学习w ...