一个sql中的一张表,最多只会走一个索引吗

news2024/11/16 0:44:56

目录

先给结论

做实验

1.根据时间范围查询

什么是key_len?

2.根据时间范围和 is_delete 查询

最左匹配原则

2.根据时间范围和 blog_type 查询

如果加上id会怎么样

并不是索引一定会走

1.IN子表数量过多

2.单次查询超过30%


先给结论

先说结论,是的。一个sql中的一张表,最多只会走一个索引!

就拿之前日记本系统的日记表举例:

DROP TABLE IF EXISTS `tbl_syn_blog`;
CREATE TABLE `tbl_syn_blog` (
  `id` int NOT NULL,
  `title` varchar(100) DEFAULT NULL,
  `user_id` int DEFAULT NULL COMMENT '用户ID',
  `blog_type` int DEFAULT NULL COMMENT '类型',
  `content` blob COMMENT '内容',
  `is_delete` varchar(1) DEFAULT '0',
  `create_date` varchar(20) DEFAULT NULL,
  `update_date` varchar(20) DEFAULT NULL,
  PRIMARY KEY (`id`),
  KEY `idx_blog_main` (`create_date`,`blog_type`,`is_delete`) USING BTREE
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb3;

这张表有一个普通联合索引idx_blog_main。 分别是:create_date, blog_type, is_delete

另外ID是主键

主键肯定有索引。

做实验

1.根据时间范围查询

explain SELECT * from tbl_syn_blog where create_date >= '2023-06-05' and create_date < '2023-06-06'

联合索引走了,key_len=63。

什么是key_len?

在Mysql中执行explain的结果中有一列为key_len,那么key_len的含义是什么呢?

key_len:表示索引使用的字节数,根据这个值可以判断索引的使用情况,特别是在组合索引的时候,判断该索引有多少部分被使用到非常重要。

索引字段的附加信息: 可以分为变长和定长数据类型讨论,当索引字段为定长数据类型时,如char,int,datetime,需要有是否为空的标记,这个标记占用1个字节(对于not null的字段来说,则不需要这1字节);对于变长数据类型,比如varchar,除了是否为空的标记外,还需要有长度信息,需要占用两个字节。

对于,char、varchar、blob、text等字符集来说,key len的长度还和字符集有关,latin1一个字符占用1个字节,gbk一个字符占用2个字节,utf8一个字符占用3个字节。

create_date字段是这样的

varchar属于变长字段,长度为20,又因为是utf8字符集,根据计算公式,create_date索引长度 = 20 * 3 + 2 + 1 = 63(utf8每个字符为3bytes,允许为NULL,加1byte,变长数据类型,加2bytes)

2.根据时间范围和 is_delete 查询

EXPLAIN SELECT
 *
FROM
 tbl_syn_blog
WHERE
 create_date >= '2023-06-05'
AND create_date < '2023-06-06'
AND is_delete = '0'

欸??

为啥没变呢,不是多了一个查询条件is_delete吗?

最左匹配原则

所谓最左前缀原则,顾名思义是最左优先,以最左边的为起点任何连续的索引都能匹配上create_dateis_delete 这两个匹配项能确保联合索引idx_blog_main被触发,但实际匹配到的只有 create_date (因为不连续)。

2.根据时间范围和 blog_type 查询

EXPLAIN SELECT
 *
FROM
 tbl_syn_blog
WHERE
 create_date >= '2023-06-05'
AND create_date < '2023-06-06'
AND blog_type = 2

create_date 和 blog_type 一起,符合最左匹配原则,并且是连续的,所以都匹配到了。

INT类型的字段,允许NULL,key_len = 4 + 1 = 5,所以总长度 = 63+5=68。

如果加上id会怎么样

EXPLAIN SELECT
 *
FROM
 tbl_syn_blog
WHERE
 create_date >= '2023-06-05'
AND create_date < '2023-06-06'
AND blog_type = 7
AND id = 3

如图,加上id作为where条件后,key_len直接变成了4,也就是说只有id的索引生效了。

这也说明了,执行器会根据具体的情况,选择最佳的索引去走,一次sql查询中,一张表最多只会走一个索引

并不是索引一定会走

有一些特殊情况,索引能触发但是不会匹配。

1.IN子表数量过多

EXPLAIN SELECT
 *
FROM
 tbl_syn_blog
WHERE
 create_date >= '2023-06-05'
AND create_date < '2023-06-06'
AND blog_type in (SELECT id from sys_blog_type)

sys_blog_type表中的id很多,有几十万,那么就导致IN子句查出来的数量很多,会导致blog_type不走索引。

2.单次查询超过30%

EXPLAIN SELECT
 *
FROM
 tbl_syn_blog
WHERE 1=1
AND  blog_type = 5
 AND create_date >= '2023-01-20'
 AND create_date < '2023-06-28'

因为上面sql中的日期范围很大,对应数量非常多,超过了总表的30%,那么执行器会认为还不如全表扫描,于是索引就失效了。

还有很多索引失效的场景,这边就不一一赘述了。

总结:一个sql中的一张表,最多只会走一个索引。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/690203.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

设计模式第14讲——享元模式(Flyweight)

目录 一、什么是享元模式 二、角色组成 三、优缺点 四、应用场景 4.1 生活场景 4.2 java场景 五、代码实现 5.0 代码结构 5.1 Bike——抽象享元类&#xff08;FlyWeight&#xff09; 5.2 具体享元类&#xff08;ConcreteFlyWeight&#xff09; 5.3 BikeFactory——享元…

layui框架学习(28:穿梭框模块)

Layui模块中的穿梭框模块transfer主要支撑穿梭框组件的显示、交互等操作。所谓穿梭框是指左右各有一个复选框列表&#xff0c;可以将左侧选中的项目移动到右边&#xff0c;后者将右侧的选中项移回左边的控件&#xff0c;其样式类似下图所示&#xff08;参考文献5-6&#xff09;…

TI AM62x工业开发板规格书(单/双/四核ARM Cortex-A53 + 单核ARM Cortex-M4F,主频1.4GHz)

1 评估板简介 创龙科技TL62x-EVM是一款基于TI Sitara系列AM62x单/双/四核ARM Cortex-A53 单核ARM Cortex-M4F多核处理器设计的高性能低功耗工业评估板&#xff0c;由核心板和评估底板组成。处理器ARM Cortex-A53(64-bit)主处理单元主频高达1.4GHz&#xff0c;ARM Cortex-M4F实…

如何使用 Flink SQL 探索 GitHub 数据集|Flink-Learning 实战营

为进一步帮助开发者学习使用 Flink&#xff0c;Apache Flink 中文社区近期发起 Flink-Learning 实战营项目。本次实战营通过真实有趣的实战场景帮助开发者实操体验 Flink&#xff0c;课程包括实时数据接入、实时数据分析、实时数据应用的场景实。并结合小松鼠助教模式&#xff…

USR-C216 WIIF连接手机

复位后连接USR-C216无线 浏览器输入10.10.100.254 账号密码为admin 客户端模式服务器地址无效&#xff0c;默认就行 打开手机网络调试助手选择客户端模式&#xff0c;输入10.10.100.254&#xff0c;端口8899 可以透传了 关于AT指令&#xff0c;先发“”&#xff0c;然后3s内发…

【数据管理架构】什么是 OLTP?

OLTP&#xff08;在线事务处理&#xff09;支持在 ATM 和在线银行、收银机和电子商务以及我们每天与之交互的许多其他服务背后进行快速、准确的数据处理。 什么是 OLTP&#xff1f; OLTP 或在线事务处理允许大量人员&#xff08;通常通过 Internet&#xff09;实时执行大量数据…

基于Vue+Node.js的宠物领养网站的设计与开发-计算机毕设 附源码83352

基于VueNode.js的宠物领养网站的 摘 要 随着互联网大趋势的到来&#xff0c;社会的方方面面&#xff0c;各行各业都在考虑利用互联网作为媒介将自己的信息更及时有效地推广出去&#xff0c;而其中最好的方式就是建立网络管理系统&#xff0c;并对其进行信息管理。由于现在网络…

【国产FPGA应用】紫光Pango Design联合 Modelsim 仿真方法

Modelsim 是 FPGA 开发中重要的 EDA 设计仿真工具&#xff0c;主要用于验证数字电路设计是否正确。我们经常用Xilinx的ISE或者Vivado与Modelsim进行联合仿真&#xff0c;其实国产FPGA开发工具也可以与Modelsim进行联合仿真&#xff0c;对于设计比较复杂的应用还是非常方便的&am…

创邻科技与浪潮信息KOS完成澎湃技术认证

近日&#xff0c;浙江创邻科技有限公司&#xff08;简称&#xff1a;创邻科技&#xff09;自主研发的Galaxybase图数据库系统与浪潮信息服务器操作系统KOS V5完成澎湃技术认证。创邻科技作为国内首个成熟的商业图数据库供应商&#xff0c;在同类厂商中率先完成认证。测试结果显…

vue3通过render函数实现一个菜单下拉框

背景说明 鼠标移动到产品服务上时&#xff0c;出现标红的下拉框。 使用纯css的方案实现最简单&#xff0c;但是没什么技术含量&#xff0c;弃之&#xff1b;使用第三方组件库&#xff0c;样式定制麻烦弃之。因此&#xff0c;我们使用vue3直接在页面创建一个dom作为下拉框吧。…

【经验分享】Docker容器部署方法说明

前 言 本案例适用开发环境&#xff1a; Windows开发环境&#xff1a;Windows 7 64bit、Windows 10 64bit Linux开发环境&#xff1a;Ubuntu 18.04.4 64bit 虚拟机&#xff1a;VMware15.1.0 Docker是一个开源的应用容器引擎&#xff0c;让开发者可打包他们的应用以及依赖包…

rust持续学习 声明宏

学习记录&#xff0c;都是学自圣经&#xff0c;macrobook啥的 https://doc.rust-lang.org/reference/macros-by-example.html macro_rules! bar {(3) > {println!("3");};(4) > {println!("4");}; }这个是入门例子&#xff0c;有点像match 调用就是…

【Java|多线程与高并发】线程池详解

文章目录 1. 线程池简介2. 创建线程池3. 工厂模式简介4. 线程池的使用5. 实现线程池6. ThreadPoolExecutor的构造方法讲解7. 线程池的线程数量,如何确定? 1. 线程池简介 Java线程池是一种用于管理和重用线程的机制&#xff0c;它可以在需要执行任务时&#xff0c;从线程池中获…

二叉树遍历方法——前、中、后序遍历(java)

二叉树结构&#xff1a; static class TreeNode{public char val;public TreeNode left;public TreeNode right;public TreeNode(char val) {this.val val;}Overridepublic String toString() {return this.val"";}} 一、前序遍历 前序遍历是一种访问二叉树的每一…

【shell脚本】沐风晓月跟你聊聊shell脚本中的case实战

前言 前面我们已经介绍了while及for循环&#xff0c;结合if语句可以构建一些简单的控制面板及菜单脚本&#xff0c;今天我们来探讨下case语句。 case选择语句&#xff0c;主要用于对多个选择条件进行匹配输出&#xff0c;与if elif语句结构类似&#xff0c;通常用于脚本传递输…

阵列模式合成第 I 部分:清零、窗口化和细化(附源码)

一、前言 本示例说明如何使用相控阵系统工具箱解决一些阵列合成问题。在相控阵设计应用中&#xff0c;通常需要找到一种方法来逐渐减小晶片响应&#xff0c;以使最终的阵列阵列模式满足某些性能标准。典型的性能标准包括主瓣位置、零位置和旁瓣电平。 二、使用旁瓣消除器消除干…

两个进程定时通过共享内存进行通信

进程1-client #include <stdio.h> #include <stdlib.h> #include <sys/ipc.h> #include <sys/shm.h> #include <unistd.h> #include <string.h>#define SHM_SIZE 10 * 1024 * 1024 // 共享内存大小为10M #define WRITE_INTERVAL 1 …

PHP 基础知识

目录 PHP基础 2 PHP代码标记 2 PHP注释 2 PHP语句分隔符 2 PHP变量 3 常量 3 数据类型 4 流程控制 6 文件 7 函数 9 闭包 11 常用系统函数 12 错误处理 13 错误显示设置 15 字符串类型 17 字符串相关函数 19 数组 21 遍历数组 22 数组的相关函数 25 PHP基础 PHP是一种运行在服务…

通过netty源码带你一步步剖析NioEventLoop 的任务队列原理

NioEventLoop 的异步任务队列成员: NioEventLoop 中对newTaskQueue 接口的实现,返回的是JCTools工具包Mpsc队列(多生产者单一消费者无锁队列,(无界和有界都有实现) private static Queue<Runnable> newTaskQueue0(int maxPendingTasks) {// newMpscQueue 无界对列,newM…

10万元存款是年轻人的一个“坎”?存款超过10万就会超过53.7%的人?不要焦虑,以过来人的身份帮你分析分析!

&#x1f337; 古之立大事者&#xff0c;不惟有超世之才&#xff0c;亦必有坚忍不拔之志 &#x1f390; 个人CSND主页——Micro麦可乐的博客 &#x1f425;《Docker实操教程》专栏以最新的Centos版本为基础进行Docker实操教程&#xff0c;入门到实战 &#x1f33a;《RabbitMQ》…