数据库允许空值(null),往往是悲剧的开始(1分钟系列)
数据库字段允许空值,会遇到一些问题,此处包含的一些知识点,和大家聊一聊。
数据准备:
create table user (
id int,
name varchar(20),
index(id)
)engine=innodb;
insert into user values(1,'shenjian');
insert into user values(2,'zhangsan');
insert into user values(3,'lisi');
说明:
id为索引,非唯一(non unique),允许空(null)。
知识点1(热身):负向查询不能命中索引,会导致全表扫描。

explain select * from user where id!=1;
索引字段id上的不等于查询,如上图所示:
(1)type=ALL,全表扫描;
(2)rows=3,全表只有3行;
知识点2(划重点):允许空值,不等于(!=)查询,可能导致不符合预期的结果。

insert into user(name) values('wangwu');
先构造一条id为NULL的数据,可以看到共有4条记录。
select * from user where id!=1;
再次执行不等于查询。
你猜结果集有几条记录(共4条,不等于排除1条)?
答错了!
结果集只有2条记录,空值记录记录并未出现在结果集里。

select * from user where id!=1 or id is null;
如果想到得到符合预期的结果集,必须加上一个or条件。
画外音:恶心不恶心,这个大坑你踩过没有?
知识点3(附加):某些or条件,又可能导致全表扫描,此时应该优化为union。

explain select * from user where id=1;
索引字段id上的等值查询,能命中索引,如上图所示:
(1)type=ref,走非唯一索引;
(2)rows=1,预估扫描1行;

explain select * from user where id is null;
索引字段id上的null查询,也能命中索引,如上图所示:
(1)type=ref,走非唯一索引;
(2)rows=1,预估扫描1行;

explain select * from user where id=1 or id is null;
如果放到一个SQL语句里用or查询,则会全表扫描,如上图所示:
(1)type=ALL,全表扫描;
(2)rows=4,全表只有4行;

explain select * from user where id=1
union
select * from user where id is null;
此时应该优化为union查询,又能够命中索引了,如上图所示:
(1)type=ref,走非唯一索引;
(2)rows=1,预估扫描1行;
画外音:第三行临时表的ALL,是两次结果集的合并。
总结
(1)负向比较(例如:!=)会引发全表扫描;
(2)如果允许空值,不等于(!=)的查询,不会将空值行(row)包含进来,此时的结果集往往是不符合预期的,此时往往要加上一个or条件,把空值(is null)结果包含进来;
(3)or可能会导致全表扫描,此时可以优化为union查询;
(4)建表时加上默认(default)值,这样能避免空值的坑;
(5)explain工具是一个好东西;
希望大家有收获!
画外音:本文测试于MySQL5.6。
数据库允许空值(null),往往是悲剧的开始(1分钟系列)的更多相关文章
- 数据库允许空值(null),往往是悲剧的开始 (转)
数据库字段允许空值,会遇到一些问题,此处包含的一些知识点,和大家聊一聊. 数据准备: create table user ( id int, name varchar(20), index(id) ) ...
- 数据库允许空值(null),往往是悲剧的开始
原文: 58沈剑 架构师之路 https://mp.weixin.qq.com/s/XRSPITgWWK-2Ee-cSIqw1w 数据库字段允许空值,会遇到一些问题,此处包含的一些知识点,和大 ...
- SQL Serve数据库排序空值null始终前置的方法
[转:http://blog.knowsky.com/233986.htm] [sqlserver]: sqlserver 认为 null 最小. 升序排列:null 值默认排在最前. 要想排后面,则 ...
- sqlserver、oracle数据库排序空值null问题解决办法
转:https://www.cnblogs.com/pacer/archive/2010/03/02/1676371.html [sqlserver]: sqlserver 认为 null 最小. 升 ...
- SQL学习之空值(Null)检索
在创建表表,我们可以指定其中的列包不包含值,在一列不包含值时,我们可以称其包含空值null. 确定值是否为null,不能简单的检查是否=null.select语句有一个特殊的where子句,可用来检查 ...
- 浅谈MDX处理空值NULL及格式化结果
MDX查询结果中往往会含有"NULL"值,这是某维度下对应的的量值不存在导致的,为了让报表呈现更好的效果,在有些情况下,需要将"NULL"的切片值置换成0,这些 ...
- 数据库中的null问题
在数据库中有些列的值可以为null,这一篇,我们围绕数据库中的null来讲述. 1. null与 “”.0的区别 数据库中的null表示——不知道,“”——一个空字符串,0则是一个数值. 所以n ...
- MDX Cookbook 03 - MDX 查询中负数,零和空值 NULL 的格式化处理
FORMAT_STRING 属性在处理计算成员(通常是度量值成员)的时候会经常使用到,比如指定标准 Standard, 货币 Currency 或者 Percent 百分比格式.除此之外,还可以自定义 ...
- C#向Sql数据库插入空值的控制
string name = textBox1.Text; int age = Convert.ToInt32(textBox2.Text.Trim()); ? null : (int?)Convert ...
随机推荐
- Nginx反向代理,Nginx的TCP/UDP调度器以及Nginx常见问题处理
nginx反向代理: 方案 使用4台RHEL7虚拟机,其中一台作为Nginx代理服务器,该服务器需要配置两块网卡,IP地址分别为192.168.4.5和192.168.2.5,两台Web服务器IP地址 ...
- Linux服务器感染kerberods病毒 | 挖矿病毒查杀及分析 | (curl -fsSL lsd.systemten.org||wget -q -O- lsd.systemten.org)|sh)
概要: 一.症状及表现 二.查杀方法 三.病毒分析 四.安全防护 五.参考文章 一.症状及表现 1.CPU使用率异常,top命令显示CPU统计数数据均为0,利用busybox 查看CPU占用率之后,发 ...
- linux学习命令收集
多看看大神的博客 https://blog.csdn.net/tao934798774/article/details/79491951 ip addr 查看ip地址 ifconfig 查看i ...
- [bzoj1775][Usaco2009 Dec]Vidgame 电视游戏问题_背包dp
1775: [Usaco2009 Dec]Vidgame 电视游戏问题 题目链接:https://www.lydsy.com/JudgeOnline/problem.php?id=1775 题解: 发 ...
- 2019年5月份最热门的JavaScript开源项目
五一假期后工作的第一天,不知道你们调整好状态没有呢? 1-libpku https://github.com/lib-pku/libpku Star 15820 该项目是由一名北大在读大学生整 ...
- SQL SERVER GETDATE() 函数
定义: GETDATE() 函数从 SQL Server 返回当前的时间和日期. 语法: GETDATE() 返回值: datetime型数据 例: 声明:本文是本人查阅网上及书籍等各种资料,再加上 ...
- SqlServer中获取所有数据库,所有表,所有字段
原文:SqlServer中获取所有数据库,所有表,所有字段 一.获取所有数据库 select * from master.dbo.SysDatabases 二.获取某个库中所有表 SELECT * F ...
- 「java.util.concurrent并发包」之 ReentrantReadWriteLock
一 引言 在多线程的环境下,对同一份数据进行读写,会涉及到线程安全的问题.比如在一个线程读取数据的时候,另外一个线程在写数据,而导致前后数据的不一致性:一个线程在写数据的时候,另一个线程也在写,同样也 ...
- PHP读取xml并写入数据库示例
<?php $xml = simplexml_load_file('books.xml'); // print_r($xml); // echo "<br/>"; ...
- django进阶版3
hello... cookie与session 为什么会有cookie和session? 由于http协议是无状态的 无法记住用户是谁 cookie cookie是保存在客户端浏览器上的键值对 是服务 ...