Skip to main content

Il existe un débitmètre financier, échelle non marquée, la quantité actuelle de données est 9555695, la requête utilise la limite, le temps de requête précédent avant l'optimisation 16 S 938 ms (exécuteur: 16S 831 ms, Fetch: 107 ms), après ajustement de SQL de la manière suivante, consommer du temps 347 ms (exécution: 163 ms, extraire la respiration: 184 ms);

Activités: Les conditions de requête sont placées dans la requête de l'enfant, la requête de l'enfant ne vérifie que l'ID de clé primaire, puis utilisez la clé primaire définie dans l'enfant de requête pour interroger d'autres champs d'attributs;
Principes: Réduire les opérations
-- 优化前SQLSELECT 各种字段FROM`table_name`WHERE 各种条件LIMIT0,10;
-- 优化后SQLSELECT 各种字段FROM`table_name` main_taleRIGHTJOIN(SELECT 子查询只查主键FROM`table_name`WHERE 各种条件LIMIT0,10;) temp_table ON temp_table.主键 = main_table.主键

Rechercher une analyse principale: Pourquoi MySQL doit-il utiliser pourquoi l'effet sur la performance?



La première explication de la version MySQL: mysql> select version();+-----------+| version() |+-----------+| 5.7.17 |+-----------+1 row in set (0.00 sec)

Structure de table: mysql> desc test;+--------+---------------------+------+-----+---------+----------------+| Field | Type | Null | Key | Default | Extra |+--------+---------------------+------+-----+---------+----------------+| id | bigint(20) unsigned | NO | PRI | NULL | auto_increment || val | int(10) unsigned | NO | MUL | 0 | || source | int(10) unsigned | NO | | 0 | |+--------+---------------------+------+-----+---------+----------------+3 rows in set (0.00 sec)

] ID est la clé de clé principale, VAL est un index unique.

Transférer un certain nombre de lDonnées audacieuses, un total de 5 millions d'habitants:

mysql> selectcount(*) from test;+----------+| count(*) |+----------+| 5242882 |+----------+1 row in set (4.25 sec)
Nous savons lors de la compensation d'une énorme compensation limitée, des problèmes effectifs:


Pour atteindre l'objectif de la même manière, nous sommes souvent réécrites selon la Déclarations suivantes: mysql> select * from test where val=4 limit 300000,5;+---------+-----+--------+| id | val | source |+---------+-----+--------+| 3327622 | 4 | 4 || 3327632 | 4 | 4 || 3327642 | 4 | 4 || 3327652 | 4 | 4 || 3327662 | 4 | 4 |+---------+-----+--------+5 rows in set (15.98 sec)

La différence de temps est claire.

Pourquoi apparaît-il ci-dessus? Voyons le processus de requête:
mysql> select * from test ainner join(select id from testwhere val=4 limit 300000,5) b on a.id=b.id;+---------+-----+--------+---------+| id | val | source | id |+---------+-----+--------+---------+| 3327622 | 4 | 4 | 3327622 || 3327632 | 4 | 4 | 3327632 || 3327642 | 4 | 4 | 3327642 || 3327652 | 4 | 4 | 3327652 || 3327662 | 4 | 4 | 3327662 |+---------+-----+--------+---------+5 rows in set (0.38 sec) Data requête le bouton Index Leaf. Selon la valeur principale de la valeur de la clé principale, la valeur totale de la valeur de champ nécessaire est interrogée.

Si loin, il est nécessaire d'interroger le bouton 300 000 fois, interrogez les données de l'indice en cluster 300005 et enfin le résultat filtré à partir des 300 000 premiers 000, et 5 seront éventuellement supprimés. MySQL a passé une vrac d'E / S aléatoire sur les données d'index de cluster et les requêtes d'E / S aléatoires n'apparaissent pas dans le jeu de résultats.

Certaines personnes demanderont: depuis le début de l'indexation, pourquoi ne pas prendre l'index de nodét feuille avec les 5 boutons nécessaires, puis interroger le LIRéel dans l'indice de cluster. Cela nécessite seulement 5 E / S aléatoires, similaires au processus de l'image suivante:



je souhaite également poser cette question.

Suite, nous avons confirmé l'inférence ci-dessus:

pour confirmer la sélection * de l'essai dans cette date limite de sexe 300000, 5 est à Scan 300005 Boutons d'index et boutons de données Au-dessus de 300005 Index de cluster, nous devons savoir qu'il n'existe aucun moyen de faire appel aux boutons de données dans SQL dans SQL. J'ai essayé la première série Handler_read_ * et je regrette qu'il n'y ait pas de variables pour répondre aux conditions.


Je ne peux que confirmer par indirectement:
InnoDB a une piscine. Il existe des pages de données récentes, y compris des pages de données et des pages d'index. Par conséquent, nous devons exécuter deux SQL pour comparer le nombre de pages de données dans le groupe tampon. Les résultats prévus sont en cours d'exécution * à partir de la vérification de participation interne (sélectionnez ID de l'enregistrement dans lequel Val = 4 limites300000, 5); Après, le nombre de pages de données dans le groupe tampon est beaucoup moins que SELECT * à partir du test où VAL = 4 limite 300000 5; Le numéro correspondant, car le précédent SQL accède uniquement à 5 pages de données, puis SQL accède à 300 000 pages de données.

On peut voir qu'il n'y a pas de pages de données pour la table d'essai dans le groupe tampon.

On peut constater qu'il y a 4098 pages de données sur la table d'essai dans le groupe tampon, 208 pages d'index.

select * from test where val=4 limit 300000,5 Sélectionnez * Dans le test de participation interne (sélectionnez l'ID de test dans lequel Val = 4 limite 300000, 5); Pour éviter l'impact du test final, nous devons vider le groupe tampon et redémarrer MySQL.
mysql> select index_name,count(*) from information_schema.INNODB_BUFFER_PAGEwhere INDEX_NAME in('val','primary') and TABLE_NAME like'%test%'groupby index_name;Empty set (0.04 sec)

Exécution de SQL:

mysql> select * fromtestwhere val=4limit300000,5;+---------+-----+--------+| id | val | source |+---------+-----+--------+| 3327622 | 4 | 4 || 3327632 | 4 | 4 || 3327642 | 4 | 4 || 3327652 | 4 | 4 || 3327662 | 4 | 4 |+---------+-----+--------+5 rows in set (26.19 sec)mysql> select index_name,count(*) from information_schema.INNODB_BUFFER_PAGE where INDEX_NAME in('val','primary') and TABLE_NAME like'%test%'groupby index_name;+------------+----------+| index_name | count(*) |+------------+----------+| PRIMARY | 4098 || val | 208 |+------------+----------+2 rows in set (0.04 sec)

Nous pouvons voir la différence entre les deux: SQL Plus de premières pages de données 4098 dans le groupe tampon et la seconde SQL Télécharge uniquement 5 pages de données dans le groupe tampon. Nos prévisionnistes sont. Cela confirme également pourquoi le premier SQL sera lent: Lisez beaucoup de flux de données inutiles (300000), mais finalement abandonner. Et cela causera un problème: télécharger de nombreux points chauds ne sont pas très élevés, le groupe tampon polluera le réservoir tampon, occuper un réservoir tampon d'espace. Assurez-vous
Pour assurer le groupe tampon vide à chaque redémarrage, nous devons désactiver Innodb_buffer_pool_dump_at_shutdown et innodb_buffer_pool_load_at_startup, peuvent contrôler les données dans le groupe de tampons lorsque la base de données activée et les données sont activées dans la base de données.Les données du groupe tampon sont sauvegardées sur le disque.

Informations de référence du mardi mysqladmin shutdown/usr/local/bin/mysqld_safe &
HTTPS: //Explainextendendends.com/2009/10/23/mysql-ord-by-limit-Performance-late-row-lookUps / ] 2 .Https: //dev.mysql.com/doc/refman/7/7/fr/innodb-information-schema-buffer-pool-tables.html

Sujets

Catégories