关于问题Mysql 怎样优化处理?一共有 5 位热心网友为你解答:
【1】、来自网友【程序员德鲁小哥】的最佳回答:
MySQL 性能优化基本上是面试必问的内容,涉及到很多场景,感觉最主要的还是索引把,基本上把每条 sql 的查询都用上索引都不会特别差,所以合理的建立索引很重要,怎么查看 sql 执行有没有用到索引,用到那些索引,这个就要看 sql 的执行计划了,下面推荐两篇 MySQL 性能优化的干货,里面有各种场景的案例,看完还不会优化 sql 私信我
【2】、来自网友【大数据 java 架构师】的最佳回答:
1. 避免使用 select * 你需要什么信息,就查询什么信息,查询的多了,查询的速度肯定就会慢
2. 当你只需要查询出一条数据的时候,要使用 limit 1 比如你要查询数据中是否有男生,只要查询一条含有男生的记录就行了,后面不需要再查了,使用 Limit 1 可以在找到一条数据后停止搜索
3. 建立高性能的索引 索引不是随便加的也不是索引越多越好,更不是所有索引对查询都有效
4. 建数据库表时,给字段设置固定合适的大小. 字段不能设置的太大,设置太大就造成浪费,会使查询速度变慢
5. 要尽量使用 not null
6. EXPLAIN 你的 SELECT 查询 使用 EXPLAIN,可以帮助你更了解 MySQL 是如何处理你的 sql 语句的, 你可以查看到 sql 的执行计划,这样你就能更好的去了解你的 sql 语句的不足,然后优化语句.
7. 在 Join 表的时候,被用来 Join 的字段,应该是相同的类型的,且字段应该是被建过索引的,这样,MySQL 内部会启动为你优化 Join 的 SQL 语句的机制。
8. 如果你有一个字段,比如“性别”,“国家”,“民族”, “省份”,“状态”或“部门”,这些字段的取值是有限而且固定的,那么,应该使用 ENUM 而不是 VARCHAR。
因为在 MySQL 中,ENUM 类型被当作数值型数据来处理,而数值型数据被处理起来的速度要比文本类型快得多。这样,我们又可以提高数据库的性能。
9. 垂直分割 将常用和有关系的字段放在相同的表中,把一张表的数据分成几张表 这样可以降低表的复杂度和字段的数目,从而达到优化的目的
10. 优化 where 查询
①. 避免在 where 子句中对字段进行表达式操作
比如: select 列 from 表 where age*2=36; 建议改成 select 列 from 表 where age=36/2;
②. 应尽量避免在 where 子句中使用 !=或 操作符,否则将引擎放弃使用索引而进行全表扫描。
③. 应尽量避免在 where 子句中对字段进行 null 值 判断
④. 应尽量避免在 where 子句中使用 or 来连接条件
11. 不建议使用%前缀模糊查询,这种查询会导致索引失效而进行全表扫描
例如 LIKE “%name”或者 LIKE “%name%这两种都是不建议的.但是可以使用 LIKE “name%”。
对于 LIKE “%name%,可以使用全文索引的形式
12. 要慎用 in 和 not in
例如:select id from t where num in(1,2,3) 建议改成 select id from t where num between 1 and 3
对于连续的数值,能用 between 就不要用 in 了
13. 理解 in 和 exists, not in 和 not exists 的区别
很多时候用 exists 代替 in 是一个好的选择:如查询语句使用了 not in 那么内外表都进行全表扫描,没用到索引,而 not exists 子查询依然能用到表上索引,所以无论哪个表大,用 not exists 都比 not in 要快。
select num from a where num in(select num from b)
建议改成: select num from a where exists(select 1 from b where num=a.num)
区分 in 和 exists 主要是造成了驱动顺序的改变(这是性能变化的关键),如果是 exists,那么以外层表为驱动表,先被访问,如果是 IN,那么先执行子查询。所以 IN 适合于外表大而内表小的情况;EXISTS 适合于外表小而内表大的情况。
关于 not in 和 not exists,推荐使用 not exists,不仅仅是效率问题,not in 可能存在逻辑问题
14. 理解 select Count (*)和 Select Count(1)以及 Select Count(column)区别
一般情况下,Select Count (*)和 Select Count(1)两着返回结果是一样的
假如表沒有主键(Primary key), 那么 count(1)比 count(*)快,
如果有主键的話,那主键作为 count 的条件时候 count(主键)最快
如果你的表只有一个字段的话那 count(*)就是最快的
count(*) 跟 count(1) 的结果一样,都包括对 NULL 的统计,而 count(column) 是不包括 NULL 的统计
技术交流请关注“大数据 java 架构师”
【3】、来自网友【美的像首诗】的最佳回答:
我认为可以大致从一下几个方面考虑:
1、表结构优化。
根据当前和未来可能扩展的业务需求,合理设计表结构,合理拆分或合并,减少数据冗余。
2、索引优化。
根据数据库各个表的查询业务设计合理的查询索引。可以参考 《数据库索引设计与优化》一书。优化系统存在的慢查询,分析原因,对症下药。
3、考虑读写读写分离,小型数据库集群构建。或者查分相关业务到其他数据库,比如 redis, ES 等。
【4】、来自网友【pigeon20046】的最佳回答:
MySQL 作为轻量级的互联网数据库先进代表以后应该往企业级应用领域发展。如 ORACLE 和 SQLSERVER 数据库系统那样除了拥有自己强大的核心数据库存储技术之外,还应该在索引,并发,安全和分布式领域拓展发展,能做成如 ORACLE ERP 企业级应用需要的集成开发工具,能实现 SQLSERVER 数据库的虚拟化系统需要,从而能更好地支持 PHP,C++,DELPHI 和 JAVA 等开发语言的多种实际应用。
【5】、来自网友【爱可生云数据库】的最佳回答:
我们知道,MySQL 一直依赖对 count(*) 的执行很头疼。很早的时候,MyISAM 引擎自带计数器,可以秒回;不过 InnoDB 就需要实时计算,所以很头疼。以前有多方法可以变相解决此类问题,比如:1. 模拟 MyISAM 的计数器比如表 ytt1,要获得总数,我们建立两个触发器分别对 insert/delete 来做记录到表 ytt1_count,这样只需要查询表 ytt1_count 就能拿到总数。ytt1_count 这张表足够小,可以长期固化到内存里。不过缺点就是有多余的触发器针对 ytt1 的每行操作,写性能降低。这里需要权衡。
2. 用 MySQL 自带的 sql_calc_found_rows 特性来隐式计算
依然是表 ytt1,不过每次查询的时候用 sql_calc_found_rows 和 found_rows() 来获取总数,比如:
- 1 row in set, 1 warning (0.00 sec)
- 这样的好处是写法简单,用的是 MySQL 自己的语法。缺点也有,大概有两点:1. sql_calc_found_rows 是全表扫。2. found_rows() 函数是语句级别的存储,有很大的不确定性,所以在 MySQL 主从架构里,语句级别的行级格式下,从机数据可能会不准确。不过行记录格式改为 ROW 就 OK。所以最大的缺点还是第一点。
- 从 warnings 信息看,这种是 MySQL 8.0 之后要淘汰的语法。3. 从数据字典里面拿出来粗略的值那这样的适合新闻展示,比如行数非常多,每页显示几行,一般后面的很多大家也都不怎么去看。缺点是数据不是精确值。4. 根据表结构特性特殊的取值
- 这里假设表 ytt1 的主键是连续的,并且没有间隙,那么可以直接 mysql> select max(id) as cnt from ytt1; +——+ | cnt | +——+ | 3072 | +——+ 1 row in set (0.00 sec)
- 不过这种对表的数据要求比较高。5. 标准推荐取法(MySQL 8.0.17 建议)
- MySQL 8.0 建议用常规的写法来实现。
- 第五种写法是 MySQL 8.0.17 推荐的,也就是说以后大部分场景直接实时计算就 OK 了。MySQL 8.0.17 以及在未来的版本都取消了 sql_calc_found_rows 特性,可以查看第二种方法里的 warnings 信息。相比 MySQL 5.7,8.0 对 count(*) 做了优化,没有必要在用第二种写法了。我们来看看 8.0 比 5.7 在此类查询是否真的有优化?MySQL 5.7
以上就是关于问题【Mysql 怎样优化处理?】的全部回答,希望能对大家有所帮助,内容收集于网络仅供参考,如要实行请慎重,任何后果与本站无关!