Mysql 的不准確


Mysql Mysql 的不准確

Mysql的統計信息不准確

即使做了表分析,information_schema.tables 中的 DATA_LENGTH,TABLE_ROWS,AVG_ROW_LENGTH,INDEX_LENGTH 也都不是准確值

mysql> select table_schema,table_name,DATA_LENGTH,TABLE_ROWS,AVG_ROW_LENGTH,INDEX_LENGTH from information_schema.tables where table_name='isc_message1';
+--------------+--------------+-------------+------------+----------------+--------------+
| TABLE_SCHEMA | TABLE_NAME   | DATA_LENGTH | TABLE_ROWS | AVG_ROW_LENGTH | INDEX_LENGTH |
+--------------+--------------+-------------+------------+----------------+--------------+
| test         | isc_message1 |  2086649856 |    3844654 |            542 |     62488576 |
+--------------+--------------+-------------+------------+----------------+--------------+
1 row in set (0.00 sec)

insert into isc_message1(channel_code,create_time) values('2020030701','20200307');
insert into isc_message1(channel_code,create_time) values('2020030702','20200307');

mysql> select table_schema,table_name,DATA_LENGTH,TABLE_ROWS,AVG_ROW_LENGTH,INDEX_LENGTH from information_schema.tables where table_name='isc_message1';
+--------------+--------------+-------------+------------+----------------+--------------+
| TABLE_SCHEMA | TABLE_NAME   | DATA_LENGTH | TABLE_ROWS | AVG_ROW_LENGTH | INDEX_LENGTH |
+--------------+--------------+-------------+------------+----------------+--------------+
| test         | isc_message1 |  2086649856 |    3844654 |            542 |     62488576 |
+--------------+--------------+-------------+------------+----------------+--------------+
1 row in set (0.00 sec)
mysql> analyze table isc_message1;
+-------------------+---------+----------+----------+
| Table             | Op      | Msg_type | Msg_text |
+-------------------+---------+----------+----------+
| test.isc_message1 | analyze | status   | OK       |
+--------------------------+---------+----------+----------+
1 row in set (0.30 sec)
mysql> select table_schema,table_name,DATA_LENGTH,TABLE_ROWS,AVG_ROW_LENGTH,INDEX_LENGTH from information_schema.tables where table_name='isc_message1';
+--------------+--------------+-------------+------------+----------------+--------------+
| TABLE_SCHEMA | TABLE_NAME   | DATA_LENGTH | TABLE_ROWS | AVG_ROW_LENGTH | INDEX_LENGTH |
+--------------+--------------+-------------+------------+----------------+--------------+
| test         | isc_message1 |  2086649856 |    4021903 |            518 |     62488576 | 
+--------------+--------------+-------------+------------+----------------+--------------+
1 row in set (0.00 sec)
mysql> select count(1) from isc_message1;
+----------+
| count(1) |
+----------+
|  3607910 |
+----------+
1 row in set (1.43 sec)
mysql> optimize table  isc_message1;
+-------------------+----------+----------+-------------------------------------------------------------------+
| Table             | Op       | Msg_type | Msg_text                                                          |
+-------------------+----------+----------+-------------------------------------------------------------------+
| test.isc_message1 | optimize | note     | Table does not support optimize, doing recreate + analyze instead |
| test.isc_message1 | optimize | status   | OK                                                                |
+-------------------+----------+----------+-------------------------------------------------------------------+
2 rows in set (1 min 10.41 sec)
mysql> select table_schema,table_name,DATA_LENGTH,TABLE_ROWS,AVG_ROW_LENGTH,INDEX_LENGTH from information_schema.tables where table_name='isc_message1';
+--------------+--------------+-------------+------------+----------------+--------------+
| TABLE_SCHEMA | TABLE_NAME   | DATA_LENGTH | TABLE_ROWS | AVG_ROW_LENGTH | INDEX_LENGTH |
+--------------+--------------+-------------+------------+----------------+--------------+
| test         | isc_message1 |  2086649856 |    4606909 |            452 |     62488576 |
+--------------+--------------+-------------+------------+----------------+--------------+
1 row in set (0.00 sec)

mysql> select 3844654*542,4021903*518,4606909*452;
+-------------+-------------+-------------+
| 3844654*542 | 4021903*518 | 4606909*452 |
+-------------+-------------+-------------+
|  2083802468 |  2083345754 |  2082322868 |
+-------------+-------------+-------------+
1 row in set (0.00 sec)

注意:
1.DATA_LENGTH,INDEX_LENGTH一直沒變化,即使收集了統計信息。說明Mysql統計信息收集也不是很准確,畢竟分析表完成的很快(300w行0.3s就完成了分析),也可能數據變化太小。
2.TABLE_ROWS,AVG_ROW_LENGTH 變化比較誇張,但肯定不符合實際情況,而他們的乘積卻相對穩定些,上面顯示變化在1M 以內

Mysql 執行計划的不靠譜

ID 是主鍵
create_time 可為空輔助索引

mysql> desc select count(1) from isc_message1;
+----+-------------+--------------+------------+-------+---------------+-------------+---------+------+---------+----------+-------------+
| id | select_type | table        | partitions | type  | possible_keys | key         | key_len | ref  | rows    | filtered | Extra       |
+----+-------------+--------------+------------+-------+---------------+-------------+---------+------+---------+----------+-------------+
|  1 | SIMPLE      | isc_message1 | NULL       | index | NULL          | create_time | 6       | NULL | 3772852 |   100.00 | Using index |
+----+-------------+--------------+------------+-------+---------------+-------------+---------+------+---------+----------+-------------+
1 row in set, 1 warning (0.00 sec)
mysql>  desc select count(*) from isc_message1;
+----+-------------+--------------+------------+-------+---------------+-------------+---------+------+---------+----------+-------------+
| id | select_type | table        | partitions | type  | possible_keys | key         | key_len | ref  | rows    | filtered | Extra       |
+----+-------------+--------------+------------+-------+---------------+-------------+---------+------+---------+----------+-------------+
|  1 | SIMPLE      | isc_message1 | NULL       | index | NULL          | create_time | 6       | NULL | 3772852 |   100.00 | Using index |
+----+-------------+--------------+------------+-------+---------------+-------------+---------+------+---------+----------+-------------+
1 row in set, 1 warning (0.00 sec)

mysql> desc select count(id) from isc_message1;
+----+-------------+--------------+------------+-------+---------------+-------------+---------+------+---------+----------+-------------+
| id | select_type | table        | partitions | type  | possible_keys | key         | key_len | ref  | rows    | filtered | Extra       |
+----+-------------+--------------+------------+-------+---------------+-------------+---------+------+---------+----------+-------------+
|  1 | SIMPLE      | isc_message1 | NULL       | index | NULL          | create_time | 6       | NULL | 3772852 |   100.00 | Using index |
+----+-------------+--------------+------------+-------+---------------+-------------+---------+------+---------+----------+-------------+
1 row in set, 1 warning (0.00 sec)

mysql> desc select count(create_time) from isc_message1;
+----+-------------+--------------+------------+-------+---------------+-------------+---------+------+---------+----------+-------------+
| id | select_type | table        | partitions | type  | possible_keys | key         | key_len | ref  | rows    | filtered | Extra       |
+----+-------------+--------------+------------+-------+---------------+-------------+---------+------+---------+----------+-------------+
|  1 | SIMPLE      | isc_message1 | NULL       | index | NULL          | create_time | 6       | NULL | 3772852 |   100.00 | Using index |
+----+-------------+--------------+------------+-------+---------------+-------------+---------+------+---------+----------+-------------+
1 row in set, 1 warning (0.00 sec)

mysql> desc format=json select count(create_time) from isc_message1;
+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| EXPLAIN                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                 |
+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| {
  "query_block": {
    "select_id": 1,
    "cost_info": {
      "query_cost": "504644.20"
    },
    "table": {
      "table_name": "isc_message1",
      "access_type": "index",
      "key": "create_time",
      "used_key_parts": [
        "create_time"
      ],
      "key_length": "6",
      "rows_examined_per_scan": 3772852,
      "rows_produced_per_join": 3772852,
      "filtered": "100.00",
      "using_index": true,
      "cost_info": {
        "read_cost": "127359.00",
        "eval_cost": "377285.20",
        "prefix_cost": "504644.20",
        "data_read_per_join": "101G"
      },
      "used_columns": [
        "create_time"
      ]
    }
  }
} |
+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
1 row in set, 1 warning (0.00 sec)

mysql> desc format=json select count(1) from isc_message1;           
+----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| EXPLAIN                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                          |
+----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| {
  "query_block": {
    "select_id": 1,
    "cost_info": {
      "query_cost": "504644.20"
    },
    "table": {
      "table_name": "isc_message1",
      "access_type": "index",
      "key": "create_time",
      "used_key_parts": [
        "create_time"
      ],
      "key_length": "6",
      "rows_examined_per_scan": 3772852,
      "rows_produced_per_join": 3772852,
      "filtered": "100.00",
      "using_index": true,
      "cost_info": {
        "read_cost": "127359.00",
        "eval_cost": "377285.20",
        "prefix_cost": "504644.20",
        "data_read_per_join": "101G"
      }
    }
  }
} |
+----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
1 row in set, 1 warning (0.00 sec)
mysql> select count(create_time) from isc_message1;
+--------------------+
| count(create_time) |
+--------------------+
|            3157925 |
+--------------------+
1 row in set (0.47 sec)

mysql> select count(*) from isc_message1;           
+----------+
| count(*) |
+----------+
|  3607910 |
+----------+
1 row in set (0.28 sec)

mysql> select count(id) from isc_message1; 
+-----------+
| count(id) |
+-----------+
|   3607910 |
+-----------+
1 row in set (0.33 sec)

mysql> select count(1) from isc_message1;  
+----------+
| count(1) |
+----------+
|  3607910 |
+----------+
1 row in set (0.28 sec)

mysql> select count(1) from isc_message1;
+----------+
| count(1) |
+----------+
|  3607910 |
+----------+
1 row in set (0.29 sec)

mysql> select count(create_time) from isc_message1; 
+--------------------+
| count(create_time) |
+--------------------+
|            3157925 |
+--------------------+
1 row in set (0.45 sec)

mysql> select count(id) from isc_message1;           
+-----------+
| count(id) |
+-----------+
|   3607910 |
+-----------+
1 row in set (0.34 sec)

注意:
通過以上可知,做count統計時
count(1)和count(*)的效率差不多,都比較高,而且准確
count(主鍵) 效率稍低,結果准確
count(可為空輔助索引) 效率低,結果不准確
而這幾個count的執行計划,都不准確。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM