zoukankan      html  css  js  c++  java
  • MySQL性能优化

    一、优化思路

      数据查询慢,不代表 SQL 语句写法有问题。 首先,我们需要找到问题的源头才能“对症下药”。用一张流程图展示 MySQL 优化的思路:

         从图中可以清楚地看出,导致数据查询慢的原因有多种,如:缓存失效,在此一段时间内由于高并发访问导致 MySQL 服务器崩溃;SQL 语句编写问题;MySQL 服务器参数问题;硬件配置限制 MySQL 服务性能问题等。

    二、查看 MySQL 服务器运行的状态值

        如果系统的并发请求数不高,且查询速度慢,可以忽略该步骤直接进行 SQL 语句调优步骤。执行命令:

    show status
    

       由于返回结果太多,此处不贴出结果。其中,再返回的结果中,我们主要关注 “Queries”、“Threads_connected” 和 “Threads_running” 的值,即查询次数、线程连接数和线程运行数。

      我们可以通过执行如下脚本监控 MySQL 服务器运行的状态值:

    #!/bin/bash
    while true
    do
    mysqladmin -uroot -p"密码" ext | awk '/Queries/{q=$4}/Threads_connected/{c=$4}/Threads_running/{r=$4}END{printf("%d %d %d
    ",q,c,r)}' >> status.txt
    sleep 1
    done
    

      执行该脚本 24 小时,获取 status.txt 里的内容,再次通过 awk 计算:每秒请求 MySQL 服务的次数

    awk '{q=$1-last;last=$1}{printf("%d %d %d
    ",q,$2,$3)}'>> status.txt
    

      如果观察的数据有周期性的变化,需要修改缓存失效策略。

    三、获取需要优化的SQL语句

       方式一:查看运行的线程

       执行命令:

    show processlist
    

      返回结果:

    mysql> show processlist;
    +----+------+-----------+------+---------+------+----------+------------------+
    | Id | User | Host      | db   | Command | Time | State    | Info          
    +----+------+-----------+------+---------+------+----------+------------------+
    |  9 | root | localhost | test | Query   |    0 | starting | show processlist 
    +----+------+-----------+------+---------+------+----------+------------------+
    1 row in set (0.00 sec)
    

     从返回结果中我们可以了解该线程执行了什么命令/SQL 语句以及执行的时间。实际应用中,查询的返回结果会有 N 条记录。其中,返回的 State 的值是我们判断性能好坏的关键,其值出现如下内容,则该行记录的 SQL 语句需要优化:

    Converting HEAP to MyISAM # 查询结果太大时,把结果放到磁盘,严重
    Create tmp table #创建临时表,严重
    Copying to tmp table on disk  #把内存临时表复制到磁盘,严重
    locked #被其他查询锁住,严重
    loggin slow query #记录慢查询
    Sorting result #排序
    

       方式二:开启慢查询日志

       在配置文件 my.cnf 中的 [mysqld] 一行下边添加两个参数:

    slow_query_log = 1
    slow_query_log_file=/var/lib/mysql/slow-query.log
    long_query_time = 2
    
    log_queries_not_using_indexes = 1
    

     其中,slow_query_log = 1 表示开启慢查询;

                  slow_query_log_file 表示慢查询日志存放的位置;

                  long_query_time = 2 表示查询 >=2 秒才记录日志;

                  log_queries_not_using_indexes = 1 记录没有使用索引的 SQL 语句。

      注意:slow_query_log_file 的路径不能随便写,否则 MySQL 服务器可能没有权限将日志文件写到指定的目录中。建议直接复制上文的路径。

     修改保存文件后,重启 MySQL 服务。在 /var/lib/mysql/ 目录下会创建 slow-query.log 日志文件。连接 MySQL 服务端执行如下命令可以查看配置情况。

    show variables like 'slow_query%';
    
    show variables like 'long_query_time';
    

      测试慢查询日志:

    mysql> select sleep(2);
    +----------+
    | sleep(2) |
    +----------+
    |        0 |
    +----------+
    1 row in set (2.00 sec)
    

      打开慢查询日志文件

    [root@localhost mysql]# vim /var/lib/mysql/slow-query.log
    /usr/sbin/mysqld, Version: 5.7.19-log (MySQL Community Server (GPL)). started with:
    Tcp port: 0  Unix socket: /var/lib/mysql/mysql.sock
    Time                 Id Command    Argument
    # Time: 2017-10-05T04:39:11.408964Z
    # User@Host: root[root] @ localhost []  Id:     3
    # Query_time: 2.001395  Lock_time: 0.000000 Rows_sent: 1  Rows_examined: 0
    use test;
    SET timestamp=1507178351;
    select sleep(2);
    

     我们可以看到刚才执行了 2 秒的 SQL 语句被记录下来了。虽然在慢查询日志中记录查询慢的 SQL 信息,但是日志记录的内容密集且不易查阅。因此,我们需要通过工具将 SQL 筛选出来.

       MySQL 提供 mysqldumpslow 工具对日志进行分析。我们可以使用 mysqldumpslow --help 查看命令相关用法

       常用参数如下:

      -s:排序方式,后边接着如下参数
            c:访问次数
            l:锁定时间
            r:返回记录
            t:查询时间
        al:平均锁定时间
        ar:平均返回记录书
        at:平均查询时间
        -t:返回前面多少条的数据
        -g:翻遍搭配一个正则表达式,大小写不敏感
    

     案例:

    获取返回记录集最多的10个sql
    mysqldumpslow -s r -t 10 /var/lib/mysql/slow-query.log
    
    获取访问次数最多的10个sql
    mysqldumpslow -s c -t 10 /var/lib/mysql/slow-query.log
    
    获取按照时间排序的前10条里面含有左连接的查询语句
    mysqldumpslow -s t -t 10 -g "left join" /var/lib/mysql/slow-query.log
    

      参见:https://juejin.im/post/59d83f1651882545eb54fc7e

  • 相关阅读:
    现代软件工程 第一章 概论 第3题——韩婧
    现代软件工程 第一章 概论 第2题——韩婧
    小组成员邓琨、白文俊、张星星、韩婧
    UVa 10892 LCM的个数 (GCD和LCM 质因数分解)
    UVa 10780 幂和阶乘 求n!中某个因子的个数
    UVa 11859 除法游戏(Nim游戏,质因子)
    Codeforces 703C Chris and Road 二分、思考
    Codeforces 703D Mishka and Interesting sum 树状数组
    hdu 5795 A Simple Nim SG函数(多校)
    hdu 5793 A Boring Question 推公式(多校)
  • 原文地址:https://www.cnblogs.com/moonandstar08/p/8570515.html
Copyright © 2011-2022 走看看