用EXPLAIN看MySQL的执行计划时经常会看到Impossible WHERE noticed after reading const tables这句话,意思是说MySQL通过读取“const tables”,发现这个查询是不可能有结果输出的。比如对下面的表和数据:
  create table t (a int primary key, b int) engine = innodb;
insert into t values(1, 1);
insert into t values(3, 1);

执行“EXPLAIN select * from t where a = 2”时就会输出“Impossible WHERE noticed after reading const tables”。

不明白所谓的“const tables”是什么意思,对MySQL在查询优化时竟然可以发现一个查询不可能输出结果更是感觉不可思议。按数据库中“传统”的做法,查询优化时只会访问模式定义和统计信息,而据我所知,数据库中使用的各种统计信息如EquiDepth、MaxDiff柱状图,MCV,属性的最大值、最小值等都不可能精确到能够断言在上述的表中不存在“a = 2”的记录。

今天看MySQL Internal手册时才总算弄明白,原来MySQL并没有什么神奇之处,这个Impossible WHERE noticed after reading const tables的结论并不是通过统计信息做出的,而是真的去实际访问了一遍数据后,发现确实没有“a = 2”的行才得出的。

当查询中对某个表指定了主键或非空唯一索引上的等值条件,从而使得最多只可能产生一条命中结果(只对该表而言)时,MySQL在EXPLAIN之前会优先根据这一条件查找出对应的记录,并用记录的实际值替换查询中所有用到来自该表的属性的地方。一个更复杂的例子如下:

  explain select * from t as t1, t as t2 where t1.a = 1 and t2.a = t1.b + 1;

的输出结果为(由于排版关系省略了一些输出内容):

+----+...+-----------------------------------------------------+
| id | ... | Extra |
+----+...+-----------------------------------------------------+
| 1 | ... | Impossible WHERE noticed after reading const tables |
+----+...+-----------------------------------------------------+

MySQL得出上述查询不会输出结果的步骤如下:

1、首先根据t1.a = 1条件找到一条记录(1,1);

2、将上述记录中b的值1替换查询中的t1.b,即将上述查询转化为等价的“explain select 1, 1,t2.a, t2.b from t as t2 where t2.a = 1 + 1”;

3、优化器计算常量表达式的值,即计算1+1得出结果为2;

4、优化器根据t2.a = 2条件查找,发现没有命中记录;

5、优化器最终打断出上述查询不可能输出结果。

说白了,这个“Impossible WHERE noticed after reading const tables”就不再神秘了。但从这件事,我更加感觉到MySQL是个“怪怪”的数据库,有很多地方跟惯常的做法不太一样。很多数据库会在联接时将指定了唯一索引等值条件的表优先执行,作为查询执行的第一步,但据我所知只有MySQL将这一步骤提前到查询优化的第一步来做。这么做到底在什么情况下才有好处好像是个很微妙的问题,对于本文中给出的这两个例子,在优化时还是执行时做这一步开销都没什么区别。不过这么做好像没什么坏处。

这么会导致一个“怪怪”的现象,那就是EXPLAIN有时候也会被阻塞。比如“EXPLAIN select * from t where a = 2 lock in share mode”,同时又有另一个事务插入了一条a = 2的记录而没有提交时,EXPLAIN就会在那里等锁。

        </div>

MySQL特异功能之:Impossible WHERE noticed after reading const tables的更多相关文章

  1. MySQL:浅析 Impossible WHERE noticed after reading const tables

    使用 EXPLAIN 执行计划的时候,在 Extra 中偶尔会看到这样的描述: Impossible WHERE noticed after reading const tables 字面上的意思是: ...

  2. 线上MySQL慢查询现象案例--Impossible WHERE noticed after reading const tables

    前言:2012年的笔记整理而得,发布个人博客,做备忘录使用. 背景:线上慢查询日志监控,得到如下的语句:       发现:select doc_text from t_wiki_doc_text w ...

  3. Impossible WHERE noticed after reading const tables

    阿里云反馈的慢SQL,执行计划返回如下:Impossible WHERE noticed after reading const tables sql很简单: SELECT * FROM deposi ...

  4. linux环境,通过rpm删除mysql包,报错:error reading information on service mysqld: Invalid argument

    问题描述: 今天在做saltstack的练习,想要通过sls的方式,在远程进行mysql数据库的安装,发现无法通过service的方式启动数据库,然后就想给删除了重新进行安装,在通过rpm -e进行删 ...

  5. MySQL错误日志显示(Got an error reading communication packets)的问题

    错误显示: 2019-05-28T12:54:08.267934+08:00 820396 [Note] Aborted connection 820396 to db: 'Databaseplatf ...

  6. canal启动报错ERROR c.a.o.canal.parse.inbound.mysql.dbsync.DirectLogFetcher - I/O error while reading from client socket

  7. MySQL Crash Course #13# Chapter 21. Creating and Manipulating Tables

    之前 manipulate 表里的数据,现在则是 manipulate 表本身. INDEX 创建多列构成的主键 自动增长的规定 查看上一次插入的自增 id 尽量用默认值替代 NULL 外键不可以跨引 ...

  8. 【mysql】【转发】Cannot proceed because system tables used by Event Scheduler were found damaged at server start

    本地:mac 10.12.3  mysql 5.6   远程:linux 7.3    mysql 5.7.18.  (远程数据库yum安装,又5.6升级到5.7)   步骤:从本地数据库导出数据到远 ...

  9. Mysql性能优化一

    下一篇:Mysql性能优化二 mysql的性能优化无法一蹴而就,必须一步一步慢慢来,从各个方面进行优化,最终性能就会有大的提升. Mysql数据库的优化技术 对mysql优化是一个综合性的技术,主要包 ...

随机推荐

  1. Linux Framebuffer驱动框架之二软件架构(未完待续)【转】

    本文转载自:http://blog.csdn.net/gqb_driver/article/details/12918547 /************************************ ...

  2. springboot 异常: Requested bean is currently in creation: Is there an unresolvable circular reference?

    2018-07-31 11:56:18.812 WARN 10316 --- [ main] ConfigServletWebServerApplicationContext : Exception ...

  3. Android+Jquery Mobile学习系列(9)-总结和代码分享

    经过一个多月的边学习边练手,学会了Android基于Web开发的毛皮,其实开发过程中用Android原生API不是很多,更多的是HTML/Javascript/Css. 个人觉得基于WebView的J ...

  4. SQL2000数据库定期自动备份与修改

    SQL2000数据库定期自动备份与修改 http://www.veryhuo.com 2009-11-19 烈火网 投递稿件 我有话说   在SQL server企业管理器中,可以设置数据库的定期自动 ...

  5. 简述RTMPDump与编译移植

    RTMPDump主页 ,RTMPDump库主要包含三部分: 1.一个基本的客户端程序 2.两个服务器程序(rtmpsrv.rtmpsuck) 3.一个支持rtmp协议的库—librtmp 下载RTMP ...

  6. 关于类和对象的进一步讨论之析构函数 C++

    析构函数也是一个特殊的成员函数.它的作用与构造函数相反.它的名字是在类名的前面加一个“~”符号.在C++中“~”是位取反运算符.当对象的生命结束时,会自动执行解析函数.以下几种情况会执行析构函数: 1 ...

  7. JavaScript 获取星期几函数

    function getDayofWeek() {            var day = "";            var time = new Date();       ...

  8. Win10切换JDK版本

    开发项目由于使用JDK版本不同,来回配置环境变量有点繁琐,用了一天百度得到的方法 1:安装不同版本的JDK,这个应该都可以完成 2:配置环境变量 CLASSPATH.;%JAVA_HOME%\lib\ ...

  9. 2013 ACM/ICPC Asia Regional Changsha Online - J

    原题戳这里. 题意: 有一未知列数a1,a2,a3.....an, 已知s[i]=a[i-1]+a[i]+a[i]  (1<i<n) s[1]=a[1]+a[2]; s[n]=a[n-1] ...

  10. 自己写的_top、_parent以及对iframe和frameset的理解

    iframe可以写在<body>标签里,如<body><iframe src="xxx"  name="xxx" style=&q ...