【SQL实战】一条SQL统计全国各地疫情分布情况

数据库88

【SQL实战】一条SQL统计全国各地疫情分布情况

-- 疫情表,三个字段:城市/地区 省份 当前确诊人数
DROP TABLE IF EXISTS yiqing;
CREATE TABLE datacenter.yiqing(
city VARCHAR(32) COMMENT '城市/地区',
province VARCHAR(32) COMMENT '省份',
current INT COMMENT '当前确认人数'
)
COMMENT='疫情信息表';

INSERT INTO yiqing
SELECT '津南区', '天津', 217 UNION ALL
SELECT '安阳', '陕西', 110 UNION ALL
SELECT '西安', '陕西', 1385 UNION ALL
SELECT '咸阳', '河南', 10 UNION ALL
SELECT '郑州', '河南', 138 UNION ALL
SELECT '南阳', '河南', 95 UNION ALL
SELECT '呼伦贝尔', '内蒙古', 5 UNION ALL
SELECT '宁波', '浙江', 55 UNION ALL
SELECT '开封', '河南', 5 UNION ALL
SELECT '金华', '浙江', 3 UNION ALL
SELECT '防城港', '广西', 2 UNION ALL
SELECT '中山', '广东', 51 UNION ALL
SELECT '大连', '辽宁', 3 ;

SELECT * FROM yiqing ORDER BY 2,1;

【SQL实战】一条SQL统计全国各地疫情分布情况

-- §§§【统计全国疫情分布情况 结果列:省份、严重程度级别、累计确诊人数】
SELECT province AS '省份'
, CASE WHEN SUM(current)>=100 THEN 'Level1' WHEN SUM(current)

【SQL实战】一条SQL统计全国各地疫情分布情况

-- §§§【统计各省份疫情分布情况 结果列:省份、疫情风险等级、城市地区数、当前确诊数。例如:河南省有3个高风险城市,确诊人数总计300人】
SELECT province AS '省份'
, CASE WHEN current>=100 THEN '高'
WHEN current>=50 AND current

【SQL实战】一条SQL统计全国各地疫情分布情况

Original: https://www.cnblogs.com/buguge/p/15797158.html
Author: buguge
Title: 【SQL实战】一条SQL统计全国各地疫情分布情况



相关阅读1

Title: 01-MySQL主从复制

问题导入

  • 在之前项目的基础功能实现中,后台管理和移动端在进行数据访问的时候,都是直接操作数据库MySQL。此时的系统有且仅有一台MySQL服务器,则可能会出现如下问题
  • ①、读和写所有压力都由一台数据库承担,压力大
  • ②、数据库服务器磁盘损坏导致数据丢失,单点故障
  • 解决方案
  • 很简单,一台服务器撑不住,那就多台服务器
  • 为了解决上述提到的两个问题,我们可以准备两台MySQL,一台主(Master)服务器,一台从(Slave)服务器 ,主库的数据变更(写、更新、删除这些操作),需要同步到从库中(主从复制)。而用户在访问我们项目时 ,如果是写操作(insert、update、delete),则直接操作主库;如果是读(select)操作,则直接操作从库(在这种读写分离的结构中,从库是可以有多个的),这种结构我们称为 读写分离

一、MySQL主从复制

  • MySQL主从复制是一个异步的复制过程,底层是基于MySQL数据库自带的 二进制日志功能,就是一台或多台MySQL数据库( Slave,从库)从另一台MySQL数据库( master,即从库)进行日志的复制,然后再解析日志并应用到自身。 最终实现从库数据和主库的数据保持一致

PS:MySQL主从复制是MySQL数据库自带功能,无需借助第三方工具
二进制日志

  • 二进制日志(binlog)记录了所有的DDL(数据定义语言)语句和DML(数据操纵语言)语句,但是不包括数据查询语句。此日志对于灾难时的数据恢复有着极其重要的作用,MySQL的主从复制,就是通过binlog实现。默认MySQL是未开启该日志的

1.1、MySQL主从复制原理

  • MySQL主从复制原理,如下图所示
  • MySQL主从复制的过程
  • ①、Master节点将数据变更写入二进制日志(binary log)
  • ②、slave将master的binary log拷贝到它的中继日志(relay log)
  • ③、slave节点重做中继日志中的事件,完成数据的同步更新
  • 过程原理
  • ①、主库开启二进制日志文件,然后主库增删改操作(DML、DDL)都会记录到二进制日志文件中
  • ②、从库通过IO thread入去二进制日志写入中继日志文件中
  • ③、从库通过SQL thread读取中继日志,把数据同步到从库中

1.2、案例环境搭建

1.2.1、前置工作

  • Step1:
  • 准备两台服务器(没条件可以使用虚拟机),并且在服务器中安装MySQL,服务器的信息如下所示
  • 数据库 IP地址 数据库版本 Master(主库) 192.168.222.135 5.7.25 Slave(从库) 192.168.222.140 5.7.25

PS:虚拟机克隆结束之后,还需要更改克隆机子的IP地址

①、cd /etc/sysconfig/network-scripts
②、vim ifcfg-ens33
③、修改IPADDR字段的值为为另一个自己网关的ip地址
  • Step2
  • 开放3306端口,或者关闭防火墙
    -
方式一:开放3306端口
firewall-cmd --zone=public --add-port=3306/tcp --permanent  // 永久开放3306端口

firewall-cmd --zone=public --list-ports // 查看端口是否开放

方式二:关闭防火墙
system stop firewalld   // 关闭防火墙

system disable firewalld    // 关闭开机自动启动

  • Step3
  • 启动数据库服务
  • systemctl start mysqld
  • 登录MySQL,验证是否正常启动(可以正常登录即可,这里就不多演示)

1.2.2、主库配置

  • Step1:修改MySQL数据库的配置文件 /etc/my.cnf
    -
log-bin=mysql-bin   #启用二进制日志
server-id=200       #设置服务器的唯一id
  • 上述配置需要配置在mysqld下
  • Step2:重启MySQL服务
  • systemctl restart mysqld
  • Step3:创建数据同步的用户并授权
  • 前置工作:查看数据库的密码复杂程度
    • MEDIUM等级的密码校验策略要求密码组成为:数字、小写字母、大写字母、特殊字符、长度至少8位 (如果觉得麻烦可以更改校验策略的等级)
  • 登录MySQL,并执行如下指令,创建用户并授权
    -
GRANT REPLICATION SLAVE ON *.* to 'coolman'@'%' identified by 'Root@root';
  • 这句SQL的作用是 创建一个用户 coolman ,密码为 Root@root ,并且给该用户授予 REPLICATION SLAVE 权限。常用于建立复制时候所需要用到的用户权限,也就是slave必须被master授权具有该权限的用户,才能通过该用户复制。
  • Step4:登录MySQL数据库,查看master同步状态
  • 执行如下SQL,记录下结果中 FilePosition的值
  • show master status;
  • *PS:上面的SQL作用是查看Master的状态,执行完此SQL后不要再执行任何操作

1.2.3、从库配置

  • Step1:修改MySQL数据库的配置文件 /etc/mycnf
  • server-id=201 #服务器唯一id
  • PS:由于该Linux是复制出来的,MySQL中还有一个 server_uuid是一样的,需要修改,否则会引起冲突
    • vim /var/lib/mysql/auto.cnf随意修改后面的字符串即可)
  • Step2:重启MySQL服务
  • systemctl restart mysqld :重启服务
  • stop slave; :登录数据库后,停止从库的服务
  • Step3:登录MySQL数据库,设置主库的地址以及同步位置
    -
change master to master_host='192.168.222.135', master_user='coolman', master_password='Root@123', master_log_file='mysql-bin.000001', master_log_pos=440;

start slave;    # 开启从库服务
  • 参数说明:
    • 参数名称 含义 master_host 主库的IP地址 master_user 访问主库进行主从复制的用户名(在主库中创建的用户) master_password 访问主库进行主从复制的用户对应的密码 master_log_file 指定从哪个日志文件开始同步(上述查询的master状态中的file和position) master_log_pos 指定从日志文件的哪个位置开始同步
  • Step4:查看从数据库的状态
  • show slave status \G;
    • MySQL命令行中的 \G表示将查询结果进行按列打印,可以使每个字段打印到单独的行(即将查到的结构旋转90度变成纵向)
  • *通过状态信息中的Slave_IO_running和Slave_SQL_running可以看出主从同步是否就绪,如果这两个参数都是Yes,表示主从同步已经配置完成。

1.3、测试

  • 主从复制的环境已经搭建好了,那么可以通过Navicat等MySQL连接工具,连接上数据库后,进行测试
  • 测试的时候,我们只需要在主数据库Master执行操作,查看从数据库Slave中是否会将数据同步过去即可
  • PS:增删改的操作一定不能在从数据库操作,否则有很大可能Slave_SQL_Running线程被终止,从而导致主从复制失败(如果真出现了两个线程中的一个被终止之后,解决方案可以参考该[CSDN博客][https://blog.csdn.net/u013829518/article/details/91869547]
  • 测试1:执行DDL操作(创建数据库)
  • 创建数据库
    • 主库
    • 从库
  • 创建表
    • 主库
    • 从库
  • 测试2:执行DML操作(增删改)
  • 增加
    • 主数据库
    • 从数据库
  • 删除
    • 主数据库
    • 从数据库
  • 修改
    • 主数据库
    • 从数据库

Original: https://www.cnblogs.com/OnlyOnYourself-lzw/p/16405900.html
Author: OnlyOnYourself-Lzw
Title: 01-MySQL主从复制

相关阅读2

Title: 【StoneDB研发日志】列式存储 delete方案调研

MySQL删除数据的方式

以MySQL 5.7为例,数据库删除数据的方式一共有以下三种:

  1. delete
  2. truncate
  3. drop

以上三种方式都可以删除数据,但是使用场景是不同的。
对于整个表进行删除的执行速度来说:
drop > truncate >> delete

MySQL删除数据的方式-delete

delete是属于数据库的DML操作语言,一般是根据条件逐行进行删除。
使用delete删除数据时,数据库只能删除数据不能删除表的结构,并且会触发数据库的事务机制。
delete执行时,会先将所删除数据缓存到rollback segment中,事务commit之后生效;
在InnoDB中,使用delete其实并不会真正的把数据删除,是一种逻辑删,数据库底层实际上只是给删除的数据做了一个已删除的标记,因此,删除数据后的表占空间大小和删除前是一样的.

MySQL删除数据的方式-drop

drop属于数据库DDL定义语言,同 truncate ,执行后立即生效,无法找回。
drop table table_name立刻释放磁盘空间 ,drop 语句将删除表的结构、被依赖的约束(constraint)、触发器(trigger)、索引(index); 依赖于该表的存储过程/函数将保留,但是变为 invalid 状态。

删除数据的方式-TianMu 引擎的支持情况

目前StoneDB的TianMu引擎是支持 truncate 语句 和 drop 语句的,但是delete语句目前还不支持。

TianMu引擎需要不需要delete?

TianMu引擎设计的初衷

TianMu是一个列式存储引擎,列式存储的出现主要是为了方便快捷查询和高效存储大量同类型的数据而设计的,主要使用场景就是OLAP场景。下面是OLAP场景的部分关键特征:
①绝大多数是读请求
②数据以相当大的批次(> 1000行)更新,而不是单行更新;或者根本没有更新。
③已添加到数据库的数据不能修改。
④对于读取,从数据库中提取相当多的行,但只提取列的一小部分。
⑤列中的数据相对较小:数字和短字符串(例如,每个URL 60个字节)
⑥处理单个查询时需要高吞吐量(每台服务器每秒可达数十亿行)
⑦事务不是必须的
⑧对数据一致性要求低

目前行业现状

支持列存储的数据库类型 是否支持delete 备注

MariaDB ColumnStore 支持 SQL Server 支持 Oracle In-Memory Column Store 支持 DB2 BLU Acceleration 支持 MySQL HeatWave 不支持 主要作为辅助引擎,支持DML同步 TiFlash 不支持 主要作为辅助引擎,支持DML同步 PolarDBIn-Memory Column Index 支持 openGauss 支持 ClickHouse 支持 非标准的DELETE操作

OLAP场景下 对于数据的delete的操作可以说没有或者频率很小,同时列式存储对比行式存储来说并不擅长数据的增删改,如果是为了极致的查询性能,完全可以舍弃 DML 操作。但是为了功能的完整性,提升产品的竞争力,目前我们也放开了 insert 和 单表的 update 的功能,delete功能暂时还不支持,未来我们将对改功能进行支持。

主流列式数据库的delete方案

本节主要讲以下三种列式存储数据库的delete方案:
openGauss
ClickHouse
PolarDB

openGauss 列存储引擎的方案

底层存储结构

openGauss底层存储结构与stonedb类似 ,存储基本单位是CU(Compression Unit,压缩单元),即表中一列的一部分数据组成的压缩数据块。行存引擎中是以行作为单位来管理,而当使用列存储时,整个表整体被按照不同列划分为若干个CU。
【SQL实战】一条SQL统计全国各地疫情分布情况
CU文件本身结构,则如下图所示。
【SQL实战】一条SQL统计全国各地疫情分布情况
每个CU对应一个CU Desc的记录,在CU desc里记录了整个CU的事务时间戳信息、CU的大小、存储位置、magic校验码、min/max等信息。
【SQL实战】一条SQL统计全国各地疫情分布情况
每张列存表还配有一张Delta表,Delta表自身为行存储表。当有少量的数据插入到一张列存表时,数据会被暂时放入Delta表,等到到达阈值或满足一定条件或操作时再行整合为CU文件。Delta表可以避免单点数据操作带来的很重的CU操作与开销。

删除策略

  • 列存储的CU中数据的删除,实际上是标记删除。删除操作,相当于是更新了CUDesc表中CU对应CUDesc记录的delete bitmap(删除位图)结构,标记列中某行对应数据已被删除,而CU文件数据不会被更改。这样可以避免删除操作带来的IO放大以及解压、压缩的高额CPU开销。这样的设计,也可以使得对于同一个CU的select(查询)和delete(删除)互不阻塞,提升并发能力。列存储CU中数据更新,则是遵循append-only(仅允许追加)原则的,即CU文件仅会向后进行延展扩充,亦或是启用新的CU文件,而不是在对应行在CU中的位置就地更新。

【SQL实战】一条SQL统计全国各地疫情分布情况

失效空间的清理

  • 由于CU以及CUDesc的元数据管理模式,原有系统中的Vacuum机制实际上并不会非常有效的清除CU中已经失效的存储空间,因为Lazy Vacuum(清理数据时,只是标识无用行的状态可以录入新数据,不会影响对表数据的操作)仅能在CUDesc级别进行操作,在多数场景下无法对CU文件本身进行清理。列存储内部如果要对列存数据表进行清理,需要执行Vacuum Full(除了清理无用行,还会合并数据块,整个过程会锁定表)操作。

ClickHouse delete 方案

特点:缺少高频率,低延迟的修改或删除已存在数据的能力。仅能用于批量删除或修改数据。
数据有序存储
ClickHouse支持在建表时,指定将数据按照某些列进行sort by。排序后,保证了相同sort key的数据在磁盘上连续存储,且有序摆放。在进行等值、范围查询时,where条件命中的数据都紧密存储在一个或若干个连续的Block中,而不是分散的存储在任意多个Block, 大幅减少需要IO的block数量。另外,连续IO也能够充分利用操作系统page cache的预取能力,减少page fault。
【SQL实战】一条SQL统计全国各地疫情分布情况

delete 策略

ClickHouse是个分析型数据库。
OLAP场景下,数据一般是不变的,因此ClickHouse对update、delete的支持是比较弱的,实际上并不支持标准的update、delete操作。
ClickHouse通过alter方式实现更新、删除,它把update、delete操作叫做mutation(突变)。
标准SQL的更新、删除操作是同步的,即客户端要等服务端返回执行结果(通常是int值);
而ClickHouse的update、delete是通过异步方式实现的,当执行update语句时,服务端立即返回,但是实际上此时数据还没变,而是排队等着。
Mutation具体过程
首先,使用where条件找到需要修改的分区;然后,重建每个分区,用新的分区替换旧的,分区一旦被替换,就不可回退;对于单独一个分区,是原子性的;但对于整个mutation,如果涉及多个分区,则不是原子性的。

PolarDB In-Memory Column Index

特点:PolarDB将列存实现为InnoDB的二级索引
在PolarDB中所有Primary Index和Secondary Index都实现为一个B+Tree。列索引在定义上是一个Index,但其实是一个虚拟的索引,用于捕获对该索引覆盖列的增删改操作。
【SQL实战】一条SQL统计全国各地疫情分布情况
如上图所示,在PolarDB中所有Primary Index和Secondary Index都实现为一个B+Tree。而列索引在定义上是一个Index,但其实是一个虚拟的索引,用于捕获对该索引覆盖列的增删改操作。
对于上面的表其主表(Primary Index)包含(C1,C2,C3,C4,C5) 5列数据, Seconary Index索引包含(C2,C1) 两列数据, 在普通二级索引中,C2与C1编码成一行保存在B+tree中。而其中的列存索引包含(C2,C3,C4)三列数据. 在实际物理存储时,会对三列进行拆分独立存储,每一列都会按写入顺序转成列存格式。
列存实现为二级索引的另一个好处是执行器的工程实现非常简单,在MySQL中已经存在覆盖索引的概念,即一个查询所需要的列都在一个二级索引中存储,则可以直接利用这个二级索引中的数据满足查询需求,使用二级索引相对于使用Primary Index可以极大减少读取的数据量进而提升查询性能。当一个查询所需要的列都被列索引覆盖时,借助列存的加速作用,可以数十倍甚至数百倍的提升查询性能。

实现为InnoDB二级索引方案的优点:

1.查询执行器的工程实现非常简单
2.可以复用InnoDB的事务处理框架
3.可以复用InnoDB的数据编码格式
4.DDL语句操作非常灵活
5.可以复用InnoDB的Redo事务日志模块
6.二级索引与主表有一样的生命周期,方便管理

列存数据组织

对ColumnIndex中每一列,其存储都使用了无序且追加写的格式,结合标记删除及后台异步compaction实现空间回收。其具体实现上有如下几个关键点:
列索引中记录按RowGroup进行组织,每个RowGroup中不同的列会各自打包形成DataPack。
每个RowGroup都采用追加写,分属每个列的DataPack也是采用追加写模式。对于一个列索引,只有个Active RowGroup负责接受新的写入。当该RowGroup写满之后即冻结,其包含的所有Datapack会转为压缩格保存到磁盘上,同时记录每个数据块的统计信息便于过滤。
列存RowGroup中每新写入一行都会分配一个RowID用作定位,属于一行的所有列都可以用该RowID计算定位,同时系统维护PK到RowID的映射索引,以支持后续的删除和修改操作。
删除操作只需要设置一个删除标记位。
更新操作采用标记删除的方式来支持,对于更新操作,首先根据RowID计算出其原始位置并设置删除标记,然后在ActiveRowGroup中写入新的数据版本。
当一个RowGroup中的无效记录超过一定阈值,则会触发后台异步compaction操作,其作用一方面是回收空间,另一方面可以让有效数据存储更加紧凑,提升分析型查询单的效率。
【SQL实战】一条SQL统计全国各地疫情分布情况

delete 策略

删除操作只需要设置一个删除标记位。
更新操作采用标记删除的方式来支持,对于更新操作,首先根据RowID计算出其原始位置并设置删除标记,然后在ActiveRowGroup中写入新的数据版本。
当一个RowGroup中的无效记录超过一定阈值,则会触发后台异步compaction操作,其作用一方面是回收空间,另一方面可以让有效数据存储更加紧凑,提升分析型查询的效率。

各列式存储的delete方案汇总

支持列存储的数据库类型 存储结构 Delete策略

MariaDB ColumnStore 固定大小的数据块+元数据 标记删除 SQL Server 列存储索引+行组+列段 标记删除 PolarDB In-Memory Column Index 列存储索引+RowGroup+DataPack+元数据 标记删除 openGauss 元数据+数据包 标记删除 ClickHouse 有序存储+分区数据包 新建分区替换

TianMu引擎 delete 功能规划

GitHub issue 链接:
https://github.com/stoneatom/stonedb/issues/343
【SQL实战】一条SQL统计全国各地疫情分布情况

TianMu引擎 delete 功能实现流程图

【SQL实战】一条SQL统计全国各地疫情分布情况

Original: https://www.cnblogs.com/yangwilly/p/16591997.html
Author: 来来士
Title: 【StoneDB研发日志】列式存储 delete方案调研

相关阅读3

Title: 精心总结十三条建议,帮你创建更合适的MySQL索引

上篇文章讲到使用MySQL的Explain命令可以分析SQL性能瓶颈,优化SQL查询,以及查看是否用到了索引。

我们都知道创建索引可以提高查询效率,但是具体该怎么创建索引?

哪些字段适合创建索引?

哪些字段又不适合创建索引?

本文跟大家一块学习一下如何创建合适数据库索引。

1. MySQL索引的分类

在创建索引之前了解一下MySQL有哪些索引,然后我们才能选择合适的索引。

常见的索引有,普通索引、唯一索引、主键索引、联合索引、全文索引等。

普通索引

普通索引就是最基本的索引,没有任何限制。

可以使用命令创建普通索引:

ALTER TABLE `table_name` ADD INDEX index_name (`column`);

唯一索引

与普通索引不同,唯一索引的列值必须唯一,允许为null。

创建方式是这样的:

ALTER TABLE `table_name` ADD UNIQUE index_name (`column`);

主键索引

主键索引是一种特殊的唯一索引,并且一张表只有一个主键,不允许为null。

创建方式是这样的:

ALTER TABLE `table_name` ADD PRIMARY KEY (`column`);

联合索引

联合索引是同时在多个字段上创建索引,查询效率更高。

创建方式是这样的:

ALTER TABLE `table_name` ADD INDEX index_name (`column1`, `column2`, `column3`);

全文索引

全文索引主要用来匹配字符串文本中关键字。

当需要字符串中是否包含关键字的时候,我们一般用like,如果是以%开头的时候,则无法用到索引,这时候就可以使用全文索引了。

创建方式是这样的:

ALTER TABLE `table_name` ADD FULLTEXT (`column`);

2. 哪些字段适合创建索引?

我总结了有以下几条:

2.1 频繁查询的字段适合创建索引

一张表的字段总会有冷热之分,很明显那些频繁使用的字段更适合为它创建索引。

2.2 在where和on条件出现的字段优先创建索引

为什么不是在select后面出现的字段优先创建索引?

因为查询SQL会先匹配on和where条件的字段,具体的匹配顺序是这样的:

from > on > join > where > group by > having > select > distinct > order by > limit

2.3 区分度高的字段适合创建索引

比如对于一张用户表来说,生日比性别的区分度更高,更适合创建索引。

可以使用下面的方式手动统计一下,每个字段的区分度,值越大,区分度越高:

select
    count(distinct birthday)/count(*),
    count(distinct gender)/count(*)
from user;

【SQL实战】一条SQL统计全国各地疫情分布情况

对于已经创建好的索引,我们还可以使用MySQL命令查看每个索引的区分度排名:

【SQL实战】一条SQL统计全国各地疫情分布情况

图中 Cardinality列表示索引的区分度排名,也被称为基数。

2.4 有序的字段适合创建索引

有序的字段在插入数据库的过程中,仍能保持B+树的索引结构,不需要频繁更新索引文件,性能更好。

3. 哪些字段不合适创建索引?

说完哪些字段适合创建索引,就有不适合创建索引的的字段。

3.1 区分度低的字段不适合创建索引。

刚才说了用户表中性别的区分度较低,不如生日字段适合创建索引。

3.2 频繁更新的字段不适合创建索引

更新字段的过程中,需要维护B+树结构,会频繁更新索引文件,降低SQL性能。

3.3 过长的字段不适合创建索引

过长的字段会占用更多的空间,不适合创建索引。

3.4 无序的字段不适合创建索引

无序的字段在插入数据库的过程中,为了维护B+树索引结构,需要频繁更新索引文件,性能较差。

4. 创建索引的其他注意事项

4.1 优先使用联合索引

查询的时候,联合索引比普通索引能更精准的匹配到所需数据。

【SQL实战】一条SQL统计全国各地疫情分布情况

图中就是在(age,name)两个字段上建立的联合索引,在B+树中的存储结构。

可以看出,是先age排序,age相等的数据,再按name排序。

对于这条查询SQL:

select age,name from user where age=18 and name='李四';

联合索引只需一次就可以查到所需数据,如果我们只在age字段上建立索引,会先匹配到age=18的三条数据,然后再逐个遍历,效率更差,所以平时应该优先使用联合索引。

4.2 使用联合索引时,区分度的字段放前面

这样可以减少查询次数,更快地匹配到所需数据。

4.3 过长字符串可以使用前缀索引

比如在匹配用户地址的时候,如果乡镇已经能区分大部分用户了,就没必要精确到街道小区了。

创建普通索引的时候,指定索引长度,就可以创建前缀索引了。

ALTER TABLE `user` ADD INDEX idx_address (address(3));

4.4 值唯一的字段,使用唯一索引

使用唯一索引,可以避免程序bug导致产生重复数据。

4.5 排序和分组字段也尽量创建索引

在order by和group by中的字段也尽量创建索引,避免使用文件排序,可以使用索引排序提供性能。

4.6 避免创建过多索引

索引好用,适度即可。创建过多的索引,会占用更多存储空间,也会严重影响SQL性能,每次更新SQL,都需要更新大量索引文件,得不偿失。

知识点总结:

【SQL实战】一条SQL统计全国各地疫情分布情况

文章持续更新,可以微信搜一搜「 一灯架构 」第一时间阅读更多技术干货。

Original: https://www.cnblogs.com/yidengjiagou/p/16538652.html
Author: 一灯架构
Title: 精心总结十三条建议,帮你创建更合适的MySQL索引