ORACLE:
SQL> create table tab2(c1 number, c2 number, c3 varchar2(10)); 表が作成されました。 SQL> declare a number; begin a := 1; for i in 1 .. 500 loop for j in 1 .. 1000 loop insert into tab2 values(a,j,'a'); commit; a := a+1; end loop; end loop; end; / PL/SQLプロシージャが正常に完了しました。 SQL> create index ind2_2 on tab2(c2); 索引が作成されました。 SQL> insert into tab2 values(9999,null,'test'); 1行が作成されました。 SQL> commit; コミットが完了しました。 SQL> exec dbms_stats.gather_table_stats(ownname=>'TEST',tabname=>'TAB2',cascade=>TRUE); PL/SQLプロシージャが正常に完了しました。 SQL> set lin 150 pages 9999 SQL> set autot traceonly exp SQL> select count(*) from tab2 where c2 is null; 実行計画 ---------------------------------------------------------- Plan hash value: 2781695375 --------------------------------------------------------------------------- | Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time | --------------------------------------------------------------------------- | 0 | SELECT STATEMENT | | 1 | 4 | 310 (1)| 00:00:01 | | 1 | SORT AGGREGATE | | 1 | 4 | | | |* 2 | TABLE ACCESS FULL| TAB2 | 1 | 4 | 310 (1)| 00:00:01 | --------------------------------------------------------------------------- Predicate Information (identified by operation id): --------------------------------------------------- 2 - filter("C2" IS NULL) SQL> select count(*) from tab2 where c2=10; 実行計画 ---------------------------------------------------------- Plan hash value: 3563712581 ---------------------------------------------------------------------------- | Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time | ---------------------------------------------------------------------------- | 0 | SELECT STATEMENT | | 1 | 4 | 4 (0)| 00:00:01 | | 1 | SORT AGGREGATE | | 1 | 4 | | | |* 2 | INDEX RANGE SCAN| IND2_2 | 500 | 2000 | 4 (0)| 00:00:01 | ---------------------------------------------------------------------------- Predicate Information (identified by operation id): --------------------------------------------------- 2 - access("C2"=10)
复制
Mysql(Innodb):
mysql> create table tab2(c1 int, c2 int, c3 varchar(10)); Query OK, 0 rows affected (0.01 sec) mysql> delimiter // mysql> create procedure my_procedure() -> begin -> DECLARE n int DEFAULT 1; -> WHILE n < 1001 DO -> insert into tab2(c1,c2,c3) value (n,n,'desc'); -> set n = n + 1; -> END WHILE; -> end -> // Query OK, 0 rows affected (0.01 sec) mysql> delimiter ; mysql> call my_procedure; Query OK, 1 row affected (0.84 sec) mysql> create index ind2_2 on tab2(c2); Query OK, 0 rows affected (0.02 sec) Records: 0 Duplicates: 0 Warnings: 0 mysql> insert into tab2 values(9999,null,'test'); Query OK, 1 row affected (0.00 sec) mysql> explain select count(*) from tab2 where c2=10; +----+-------------+-------+------------+------+---------------+--------+---------+-------+------+----------+-------------+ | id | select_type | table | partitions | type | possible_keys | key | key_len | ref | rows | filtered | Extra | +----+-------------+-------+------------+------+---------------+--------+---------+-------+------+----------+-------------+ | 1 | SIMPLE | tab2 | NULL | ref | ind2_2 | ind2_2 | 5 | const | 1 | 100.00 | Using index | +----+-------------+-------+------------+------+---------------+--------+---------+-------+------+----------+-------------+ 1 row in set, 1 warning (0.00 sec) mysql> explain select count(*) from tab2 where c2 is null; +----+-------------+-------+------------+------+---------------+--------+---------+-------+------+----------+--------------------------+ | id | select_type | table | partitions | type | possible_keys | key | key_len | ref | rows | filtered | Extra | +----+-------------+-------+------------+------+---------------+--------+---------+-------+------+----------+--------------------------+ | 1 | SIMPLE | tab2 | NULL | ref | ind2_2 | ind2_2 | 5 | const | 1 | 100.00 | Using where; Using index | +----+-------------+-------+------------+------+---------------+--------+---------+-------+------+----------+--------------------------+ 1 row in set, 1 warning (0.00 sec)
复制
结论:
Oracle的B-tree索引不存储Null,所以“c2 is null”条件的检索不能从索引中受益。
Mysql的B+tree索引也不直接不存储Null,但是“c2 is null”条件的检索能从索引中受益。
https://dev.mysql.com/doc/ref... ref_or_null works by first doing a read on the reference key, and then a separate search for rows with a NULL key value.
复制
【版权声明】本文为墨天轮用户原创内容,转载时必须标注文章的来源(墨天轮),文章链接,文章作者等基本信息,否则作者和墨天轮有权追究责任。如果您发现墨天轮中有涉嫌抄袭或者侵权的内容,欢迎发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。
评论
一个家最好的投资,就是陪伴。愿你我都能珍惜眼前的幸福,经营好我们的家庭,让日子越过越红火。
1年前

评论
Oracle的B-tree索引不存储Null,所以“c2 is null”条件的检索不能从索引中受益。
Mysql的B+tree索引也不直接不存储Null,但是“c2 is null”条件的检索能从索引中受益。
1年前

评论
数据无国界呀,日版数据库环境
3年前

评论
相关阅读
【专家有话说第五期】在不同年龄段,DBA应该怎样规划自己的职业发展?
墨天轮编辑部
1295次阅读
2025-03-13 11:40:53
Oracle RAC ASM 磁盘组满了,无法扩容怎么在线处理?
Lucifer三思而后行
777次阅读
2025-03-17 11:33:53
Oracle+Deepseek+Dify 实现数据库数据实时分析
bicewow
702次阅读
2025-03-06 09:41:49
【ORACLE】ORACLE19C在19.13版本前的一个严重BUG-24761824
DarkAthena
569次阅读
2025-03-04 14:33:31
Oracle避坑指南|同名表导出难题:如何精准排除指定用户下的表?
szrsu
534次阅读
2025-03-05 00:42:34
MySQL8.0统计信息总结
闫建(Rock Yan)
484次阅读
2025-03-17 16:04:03
2月“墨力原创作者计划”获奖名单公布
墨天轮编辑部
456次阅读
2025-03-13 14:38:19
Ogg23ai高手必看-MySQL Innodb Cluster跟oracle的亲密接触
曹海峰
453次阅读
2025-03-04 21:56:13
【ORACLE】char类型和sql优化器发生的“错误”反应
DarkAthena
406次阅读
2025-03-04 23:05:01
什么,oracle 主机用户被删了?原来是虚惊一场!
Lucifer三思而后行
405次阅读
2025-03-03 21:12:09