Optimisation des requêtes vers la base de données MySQL. Optimisation des requêtes MySQL

Pour contrôler la bordure d'un élément, utilisez la propriété border générique. Cette propriété vous permet de définir l'épaisseur, le style et la couleur de la bordure d'un élément dans une seule déclaration.

Ces trois propriétés (épaisseur de bordure, style de bordure et couleur) peuvent être définies dans une seule déclaration. Voici un exemple :

Bordures en CSS

Un bloc div avec une bordure de 3 pixels en rouge.


Vous pouvez spécifier un style de bordure sur un seul côté d'un élément. Pour ce faire, utilisez les propriétés border-top (bordure supérieure), border-right (bordure droite), border-bottom (bordure inférieure), border-left (bordure gauche).

Bordures en CSS

Un div avec des frontières différentes.


Dans cet exemple, chaque côté du bloc a une épaisseur, un style et une couleur de bordure différents.

Réfléchissez à la façon de Aide CSS vous pouvez créer une forme comme celle-ci :

Les valeurs de bordure - épaisseur, style et couleur - peuvent être définies séparément à l'aide de propriétés spéciales.

  • style de bordure - style de bordure.
  • border-width - largeur de la bordure.
  • border-color - couleur de la bordure.

Considérons chacune des valeurs séparément.

propriété de style frontière Style de bordure.

La propriété border-style définit le style de la bordure. En CSS, en Différences HTML, la bordure d'un élément peut être non seulement solide. Acceptable valeurs suivantes pour le style de bordure :

  1. none - pas de bordure (par défaut).
  2. solide - bordure solide.
  3. double - double bordure.
  4. pointillé - bordure en pointillés.
  5. pointillé - une bordure composée d'une série de points.
  6. crête - bordure "crête".
  7. rainure - bordure "groove".
  8. encart - bordure déprimée.
  9. début - bordure extrudée.

Exemples de ce à quoi ils ressemblent.

pas de frontière (aucune)


bordure solide


double bordure


bordure d'une série de points (en pointillés)


bordure pointillée


bordure de rainure


bordure de crête


bordure en retrait (en médaillon)


bordure extrudée (début)

À propos, si vous définissez la couleur de la bordure sur le noir pour le cadre faîtier, vous obtiendrez ce résultat.

Un bloc div avec une bordure noire et un style de crête.

Le cadre semble solide, mais c'est parce que le style de crête est créé en ajoutant un effet d'ombre noire, et l'effet noir n'est pas visible sur un cadre noir.

Grâce à la propriété border-style, le style de bordure peut être défini non seulement pour tous les côtés du bloc. Il est possible de définir plusieurs valeurs pour une propriété de style de bordure ; en fonction du nombre de valeurs, le style de bordure sera attribué ; numéro différent côtés du bloc. Vous pouvez définir une, deux, trois ou quatre valeurs. Regardons des exemples pour chaque cas.

Une valeur (solide) - le style de bordure est défini pour tous les côtés du bloc.


Deux valeurs (double solide) - la première valeur définit le style des côtés supérieur et inférieur, la seconde - du côté.


Trois valeurs (plein double pointillé) - la première valeur pour le côté supérieur, la seconde pour les côtés, la troisième pour le bas.


Quatre valeurs (pointillés pleins doubles) - chaque valeur pour un côté dans le sens des aiguilles d'une montre en commençant par le haut.

La propriété de largeur de frontière. Épaisseur de la bordure.

Pour définir la largeur de la bordure d'un élément, utilisez la propriété border-width. L'épaisseur de la bordure peut être définie dans n'importe quel unités absolues mesures, par exemple en pixels.

Comme la propriété border-style, la propriété peut également être définie sur une à quatre valeurs. Regardons des exemples pour chaque cas.



Exemple de code :

Épaisseur de la bordure en CSS

Une valeur (2px) - l'épaisseur de la bordure est définie pour tous les côtés du bloc.

Deux valeurs (1px 5px) - la première valeur définit l'épaisseur des côtés supérieur et inférieur, la seconde pour le côté.

Trois valeurs (1px 3px 5px) - la première valeur pour le côté supérieur, la seconde pour les côtés, la troisième pour le bas.

Quatre valeurs (1px 3px 5px 7px) - chaque valeur pour un côté dans le sens des aiguilles d'une montre en partant du haut.


Également pour la propriété border-width, il existe des valeurs sous la forme mots-clés. Il y en a trois au total :

  • mince - bordure fine;
  • épaisseur moyenne - moyenne;
  • épais - bordure épaisse ;

Épaisseur de la bordure : fine.


Épaisseur de la bordure : moyenne.


Épaisseur de la bordure : épaisse.

La propriété border-color. Couleur de la bordure.

Pour contrôler la couleur de la bordure, utilisez l'outil border-color. Les couleurs de cette propriété peuvent être définies en utilisant n'importe quelle méthode décrite dans l'article « Couleurs en CSS », à savoir :

  • Notation hexadécimale (#ff00aa) de la couleur.
  • Format RVB- RVB (255,12,110) . Format RVBA pour CSS3.
  • Formats HSL et HSLA pour CSS3.
  • Nom de la couleur, par exemple noir. Liste complète Les noms de couleurs sont donnés dans le tableau des noms de couleurs CSS.

La propriété border-color peut également avoir une à quatre valeurs et les traite de la même manière que les propriétés précédentes.

Une valeur (rouge).


Deux valeurs (rouge noir).


Trois valeurs (rouge noir jaune).


Quatre valeurs (rouge noir jaune bleu).

Revenons maintenant au problème énoncé ci-dessus et dessinons une figure :

Voici le code qui dessine une telle figure, mais de plus grande taille :

Épaisseur de la bordure en CSS



Définition des valeurs pour les côtés séparément

Il a été mentionné ci-dessus que vous pouvez spécifier les valeurs des propriétés de bordure pour un seul côté d'un bloc. Il existe des propriétés à ces fins :

  • bordure supérieure
  • bordure droite (bordure droite)
  • bordure inférieure
  • bordure gauche (bordure gauche)

Permettez-moi de vous rappeler que pour toutes les propriétés, trois valeurs​​sont spécifiées (épaisseur, style et couleur) dans n'importe quel ordre. Mais il existe des propriétés qui vous permettent de définir séparément l'épaisseur, la couleur et le style de chaque côté. L'écriture de ces propriétés est dérivée de ce qui précède.

Options de bordure supérieure (border-top).

  • border-top-color - définit la couleur de la bordure supérieure de l'élément.
  • border-top-width - définit l'épaisseur de la bordure supérieure de l'élément.
  • border-top-style - définit le style de la bordure supérieure de l'élément.

Options de bordure droite (bordure droite).

  • border-right-color - définit la couleur de la bordure droite de l'élément.
  • border-right-width - définit l'épaisseur de la bordure droite de l'élément.
  • border-right-style - définit le style de la bordure droite de l'élément.

Possibilités limite inférieure(bordure en bas).

  • border-bottom-color - définit la couleur de la bordure inférieure de l'élément.
  • border-bottom-width - définit l'épaisseur de la bordure inférieure de l'élément.
  • border-bottom-style - définit le style de la bordure inférieure de l'élément.

Options de bordure gauche (bordure gauche).

  • border-left-color - définit la couleur de la bordure gauche de l'élément.
  • border-left-width - définit l'épaisseur de la bordure gauche de l'élément.
  • border-left-style - définit le style de la bordure gauche de l'élément.

Un exemple d'utilisation de ces propriétés :

Épaisseur de la bordure en CSS

Dans cet exemple bloc div Tout d’abord, les bordures sont définies sur un style épais et solide de 3 pixels pour tous les côtés. Alors:
  • la couleur de la bordure supérieure a été redéfinie en rouge à l'aide de la propriété border-top-color,
  • en utilisant la propriété border-right-width, l'épaisseur de la bordure droite est définie sur 10px,
  • en utilisant la propriété border-bottom-style, le style de la bordure inférieure est redéfini comme double,
  • À l’aide de la propriété border-left-color, la couleur de la bordure gauche est définie sur bleu.


La propriété border-radius. Arrondir les coins des bordures.

La propriété border-radius est destinée à arrondir les coins des bordures d'un élément. Cette propriété est apparue dans CSS3 et fonctionne correctement dans tous navigateurs modernes, sauf Internet Explorer 8 (et versions antérieures).

Les valeurs peuvent être n'importe quel nombre utilisé en CSS.

Propriété Border-radius : 15px.

Si le cadre du bloc n'est pas spécifié, le congé se produit avec l'arrière-plan. Voici un exemple de bloc arrondi sans bordure, mais avec une couleur de fond :

Propriété Border-radius : 15px.

Il existe des propriétés pour arrondir chaque coin individuel d'un élément. Cet exemple les utilise tous :

Rayon de la bordure supérieure gauche : 15 px ; rayon de bordure en haut à droite : 0 ; bordure en bas à droite : 15 px ; bordure inférieure gauche : 0 ;

Propriété Border-radius : 15px.

Bien que ce code puisse être écrit dans une seule déclaration : border-radius : 15px 0 15px 0 . Le fait est que la propriété border-radius peut être définie entre une et quatre valeurs. Le tableau ci-dessous présente les règles qui régissent ces annonces.

Après avoir étudié attentivement ce tableau, vous comprendrez que le plus brève note style souhaité sera comme ceci : border-radius : 15px 0 . Il n'y a que deux significations.

Un peu de pratique

Dessiner un citron en utilisant CSS.

Voici le code d'un tel bloc :

Marge : 0 automatique ; /* Centrer le bloc */ width: 200px; hauteur : 200px ; arrière-plan : #F5F240 ; bordure : 1px solide #F0D900 ; rayon de bordure : 10px 150px 30px 150px ;

Nous avons déjà dessiné la figure :

Maintenant, laissons-en un triangle :

Le code triangulaire est :

Marge : 0 automatique ; /* Centrer le bloc */ padding: 0px; largeur : 0px ; hauteur : 0 ; bordure : 30px blanc uni ; couleur de la bordure inférieure : rouge ;

Dans le travail quotidien, vous rencontrez des erreurs assez similaires lors de l’écriture de requêtes.

Dans cet article, je voudrais donner des exemples sur la façon de NE PAS écrire de requêtes.

  • Sélectionnez tous les champs
    SELECT * FROM table

    Lors de l'écriture de requêtes, n'utilisez pas une sélection de tous les champs - "*". Listez uniquement les champs dont vous avez réellement besoin. Cela réduira la quantité de données récupérées et envoyées. N'oubliez pas non plus de couvrir les index. Même si vous avez réellement besoin de tous les champs du tableau, il est préférable de les lister. Premièrement, cela améliore la lisibilité du code. Lorsqu'on utilise un astérisque, il est impossible de savoir quels champs se trouvent dans le tableau sans le regarder. Deuxièmement, au fil du temps, le nombre de colonnes de votre table peut changer, et s'il y a aujourd'hui cinq colonnes INT, alors dans un mois, des champs TEXT et BLOB pourront être ajoutés, ce qui ralentira la sélection.

  • Requêtes dans un cycle.
    Vous devez clairement comprendre que SQL est un langage d'exploitation défini. Parfois, les programmeurs habitués à penser en termes langages procéduraux, il est difficile de réorganiser la pensée dans le langage des ensembles. Cela peut être fait tout simplement en adoptant une règle simple : « ne jamais exécuter de requêtes en boucle ». Exemples de la façon dont cela peut être fait :

    1. Échantillons
    $news_ids = get_list("SELECT news_id FROM Today_news ");
    tandis que($news_id = get_next($news_ids))
    $news = get_row("SELECT titre, corps FROM news WHERE news_id = ". $news_id);

    La règle est très simple : moins il y a de demandes, mieux c'est (bien qu'il y ait des exceptions à cela, comme toute règle). N'oubliez pas la construction IN(). Le code ci-dessus peut être écrit en une seule requête :
    SELECT titre, corps FROM Today_news INNER JOIN news USING(news_id)

    2. Insertions
    $log = parse_log();
    tandis que($record = suivant($log))
    query("INSERT INTO logs SET valeur = ". $log["value"]);!}

    Il est beaucoup plus efficace de concaténer et d’exécuter une seule requête :
    INSÉRER DANS les journaux (valeur) VALEURS (...), (...)

    3. Mises à jour
    Parfois, vous devez mettre à jour plusieurs lignes dans une seule table. Si la valeur mise à jour est la même, alors tout est simple :
    MISE À JOUR des nouvelles SET title="test" WHERE id IN (1, 2, 3).!}

    Si la valeur à modifier est différente pour chaque enregistrement, cela peut être fait avec la requête suivante :
    MISE À JOUR des nouvelles
    titre = CAS
    QUAND news_id = 1 ALORS "aa"
    QUAND news_id = 2 ALORS "bb" FIN
    OÙ news_id DANS (1, 2)

    Nos tests montrent qu'une telle requête est 2 à 3 fois plus rapide que plusieurs requêtes distinctes.

  • Effectuer des opérations sur des champs indexés
    SELECT user_id FROM utilisateurs WHERE blogs_count * 2 = $value

    Cette requête n'utilisera pas l'index, même si la colonne blogs_count est indexée. Pour qu'un index soit utilisé, aucune transformation ne doit être effectuée sur le champ indexé dans la requête. Pour de telles requêtes, déplacez les fonctions de conversion vers une autre partie :
    SELECT user_id FROM utilisateurs WHERE blogs_count = $value / 2 ;

    Exemple similaire :
    SELECT user_id FROM utilisateurs WHERE TO_DAYS(CURRENT_DATE) - TO_DAYS(enregistré)<= 10;

    N'utilisera pas d'index sur le champ enregistré, alors que
    SELECT user_id FROM utilisateurs WHERE enregistrés >= DATE_SUB(CURRENT_DATE, INTERVAL 10 DAY);
    volonté.

  • Récupérer les lignes uniquement pour compter leur nombre
    $result = mysql_query("SELECT * FROM table", $link);
    $num_rows = mysql_num_rows($result);
    Si vous devez sélectionner le nombre de lignes qui satisfont à une certaine condition, utilisez la requête de table SELECT COUNT(*) FROM plutôt que de sélectionner toutes les lignes uniquement pour compter le nombre de lignes.
  • Récupérer des lignes supplémentaires
    $result = mysql_query("SELECT * FROM table1", $link);
    while($row = mysql_fetch_assoc($result) && $i< 20) {

    }
    Si vous n'avez besoin que de n lignes de récupération, utilisez LIMIT au lieu de supprimer les lignes supplémentaires dans l'application.
  • Utilisation de ORDER BY RAND()
    SELECT * FROM table ORDER BY RAND() LIMIT 1;

    Si la table comporte plus de 4 à 5 000 lignes, alors ORDER BY RAND() fonctionnera très lentement. Il serait beaucoup plus efficace d'exécuter deux requêtes :

    Si la table a auto_increment" clé primaire et pas de lacunes :
    $rnd = rand(1, query("SELECT MAX(id) FROM table"));
    $row = query("SELECT * FROM table WHERE id = ".$rnd);

    Ou:
    $cnt = query("SELECT COUNT(*) FROM table");
    $row = query("SELECT * FROM table LIMIT ".$cnt.", 1");
    ce qui, cependant, peut également être lent s'il y a un très grand nombre de lignes dans le tableau.

  • Usage grande quantité REJOIGNEZ
    SÉLECTIONNER
    v.video_id
    un.nom,
    g.genre
    DEPUIS
    vidéos AS v
    REJOINDRE À GAUCHE
    link_actors_videos AS la ON la.video_id = v.video_id
    REJOINDRE À GAUCHE
    acteurs AS a ON a.actor_id = la.actor_id
    REJOINDRE À GAUCHE
    link_genre_video AS lg ON lg.video_id = v.video_id
    REJOINDRE À GAUCHE
    genres AS g ON g.genre_id = lg.genre_id

    Il ne faut pas oublier que lors de la connexion de tables un à plusieurs, le nombre de lignes dans la sélection augmentera à chaque JOIN suivante. cas similaires Il peut être plus rapide de diviser une telle demande en plusieurs requêtes simples.

  • Utilisation de LIMITE
    SELECT… FROM table LIMIT $start, $per_page

    Beaucoup de gens pensent qu'une telle requête renverra $per_page d'enregistrements (généralement 10 à 20) et fonctionnera donc rapidement. Cela fonctionnera rapidement pour les premières pages. Mais si le nombre d'enregistrements est important et que vous devez exécuter une requête SELECT... FROM table LIMIT 1000000, 1000020, alors pour exécuter une telle requête, MySQL sélectionnera d'abord 1000020 enregistrements, supprimera le premier million et renverra 20. Ceci peut-être pas rapide du tout. Il n’existe pas de moyen trivial de résoudre le problème. Beaucoup limitent simplement la quantité pages disponibles nombre raisonnable. Vous pouvez également accélérer demandes similaires en utilisant des index de couverture ou solutions tierces(par exemple sphinx).

  • Ne pas utiliser ON DUPLICATE KEY UPDATE
    $row = query("SELECT * FROM table WHERE id=1");

    Si($ligne)
    query("MISE À JOUR de la table SET colonne = colonne + 1 WHERE id=1")
    autre
    query("INSERT INTO table SET colonne = 1, id=1");

    Une construction similaire peut être remplacée par une requête, à condition qu'il existe une clé primaire ou unique pour le champ id :
    INSERT INTO table SET colonne = 1, id = 1 ON DUPLICATE KEY UPDATE colonne = colonne + 1

Lire

De l'auteur : un de mes amis a décidé d'optimiser sa voiture. D'abord, il a enlevé une roue, donc il a coupé le toit, puis le moteur... En général, maintenant il marche. Ce sont toutes les conséquences d’une mauvaise approche ! Par conséquent, pour que votre SGBD continue de fonctionner, l’optimisation MySQL doit être effectuée correctement.

Quand optimiser et pourquoi ?

Cela ne vaut pas la peine d'entrer dans les paramètres du serveur et de modifier à nouveau les valeurs des paramètres (surtout si vous ne savez pas comment cela pourrait se terminer). Si l'on considère ce sujet depuis le « clocher » de l'amélioration des performances des ressources Web, alors il est si vaste qu'il mérite d'être consacré à l'ensemble d'un sujet. publication scientifique en 7 tomes.

Mais je n’ai clairement pas ce genre de patience en tant qu’écrivain, et vous non plus en tant que lecteur. Nous allons le faire plus simplement et essayer de nous plonger légèrement dans le fourré de l'optimisation Serveurs MySQL et ses composants. En utilisant installation optimale Tous les paramètres du SGBD peuvent atteindre plusieurs objectifs :

Augmentez la vitesse d’exécution des requêtes.

Améliorez les performances globales du serveur.

Réduisez le temps d’attente pour le chargement des pages de ressources.

Réduisez la consommation de la capacité du serveur d’hébergement.

Réduisez la quantité d’espace que vous occupez espace disque.

Nous allons essayer de décomposer l'ensemble du sujet de l'optimisation en plusieurs points, afin qu'il soit plus ou moins clair ce qui fait bouillir la marmite.

Pourquoi configurer un serveur

Dans MySQL, l'optimisation des performances doit commencer depuis le serveur. Tout d'abord, vous devez accélérer son fonctionnement et réduire le temps de traitement des demandes. Un remède universel Pour atteindre tous les objectifs ci-dessus, il faut activer la mise en cache. Vous ne savez pas « qu'est-ce que c'est » ? Maintenant, je vais tout expliquer.

Si la mise en cache est activée sur votre instance de serveur, le système MySQL « se souvient » automatiquement de la requête saisie par l'utilisateur. Et dans la prochaine fois lorsqu'elle est répétée, le résultat de cette requête (pour l'échantillonnage) ne sera pas traité, mais extrait de la mémoire système. Il s'avère que de cette manière, le serveur « gagne » du temps lors de l'émission d'une réponse et, par conséquent, la vitesse de réponse du site augmente. Ceci s'applique également à vitesse globale téléchargements.

Dans MySQL, l'optimisation des requêtes est applicable aux moteurs et CMS qui fonctionnent sur la base de ce SGBD et PHP. Dans ce cas, le code écrit dans un langage de programmation pour générer page web dynamique demande certaines de ses parties structurelles et de son contenu (enregistrements, archives et autres taxonomies) à la base de données.

Grâce à la mise en cache activée dans MySQL, l'exécution des requêtes sur le serveur SGBD est beaucoup plus rapide. De ce fait, la vitesse de chargement de l'ensemble de la ressource augmente. Et cela a un effet positif sur expérience utilisateur, et la position du site dans les résultats de recherche.

Activer et configurer la mise en cache

Mais revenons de la théorie « ennuyeuse » à pratique intéressante. Optimisation supplémentaire Bases de données MySQL Continuons en vérifiant l'état de la mise en cache sur votre serveur de base de données. Pour ce faire, à l'aide d'une requête spéciale, nous afficherons les valeurs de toutes les variables système :

C'est une tout autre affaire.

Faisons-le petite revue les valeurs obtenues, qui nous seront utiles pour optimiser les bases de données MySQL :

have_query_cache – la valeur indique si la mise en cache des requêtes est « ON » ou non.

query_cache_type – affiche le type de cache actif. Nous avons besoin de la valeur "ON". Cela indique que la mise en cache est activée pour tous les types de sélection (commande SELECT). Sauf pour ceux qui utilisent le paramètre SQL_NO_CACHE (interdit de sauvegarder des informations sur cette requête).

Nous avons tous les paramètres définis correctement.

Nous mesurons le cache pour les index et les clés

Maintenant, vous devez vérifier combien est alloué BÉLIER pour les index et les clés. Il est recommandé de régler ce paramètre, important pour l'optimisation de la base de données MySQL, à 20-30 % de la quantité de RAM disponible sur le serveur. Par exemple, si 4 « hectares » sont alloués pour une instance de SGBD, alors n'hésitez pas à définir 32 « mètres ». Mais tout dépend des caractéristiques d'une base de données particulière et de sa structure (types) de tables.

Pour définir la valeur du paramètre, vous devez modifier le contenu fichier de configuration my.ini, qui à Denver se trouve au chemin suivant : F:\Webserver\usr\local\mysql-5.5

Ouvrez le fichier à l'aide du Bloc-notes. Ensuite, nous y trouvons le paramètre key_buffer_size et définissons la taille optimale pour votre système PC (en fonction des « hectares » de RAM). Après cela, vous devez redémarrer le serveur de base de données.

Le SGBD utilise plusieurs sous-systèmes supplémentaires (de bas niveau), et tous leurs paramètres principaux sont également spécifiés dans ce fichier configurations. Par conséquent, si vous avez besoin d'optimiser MySQL InnoDB, alors bienvenue ici. Nous étudierons ce sujet plus en détail dans l'un de nos prochains documents.

Mesurer le niveau des indices

L'utilisation d'index dans les tables augmente considérablement la vitesse de traitement et de génération d'une réponse SGBD à une requête saisie. MySQL « mesure » constamment le niveau d'index et d'utilisation des clés dans chaque base de données. Pour recevoir valeur donnée utiliser la requête :

AFFICHER LE STATUT COMME "handler_read%"

AFFICHER LE STATUT COMME "handler_read%"

Dans le résultat obtenu, nous nous intéressons à la valeur de la ligne Handler_read_key. Si le nombre qui y est indiqué est petit, cela indique que les index ne sont presque jamais utilisés dans cette base de données. Et c'est mauvais (comme le nôtre).

→ Optimisation des requêtes MySQL

MySQL dispose d'un large éventail de fonctions pour différents tris ( COMMANDER PAR), groupes ( GROUPER PAR), les associations ( REJOINDRE À GAUCHE ou REJOINDRE À DROITE) et ainsi de suite. Tous sont certes pratiques, mais dans des conditions de demandes ponctuelles. Par exemple, si vous avez personnellement besoin de rechercher quelque chose dans la base de données en utilisant un tas de tables et de liens, alors en plus des fonctions ci-dessus, vous pouvez et même devez utiliser opérateurs conditionnels SI. Erreur principale Pour les programmeurs débutants, il s'agit du désir d'appliquer de telles requêtes dans le code de travail du site. DANS dans ce cas une requête complexe est certes belle, mais nuisible. Le fait est que les opérateurs de tri, de regroupement, d'union ou de requête imbriquée ne peuvent pas être exécutés dans la RAM et utilisent disque dur pour créer des tables temporaires. Et le disque dur, comme vous le savez, est le goulot d’étranglement du serveur.

Règles d'optimisation des requêtes MySQL

1. Évitez les requêtes imbriquées

C'est le plus grave erreur. Le processus parent attendra toujours la fin du processus enfant et maintiendra à ce moment une connexion à la base de données, utilisera le disque et chargera iowait. Deux requêtes parallèles à la base de données et réalisation du filtrage nécessaire dans l'interpréteur du serveur ( Perl, PHP, etc.) sera exécuté un ordre de grandeur plus rapide que celui imbriqué.

Exemples en perl ce qu'il ne faut pas faire :

Mon $sth = $dbh->prepare("SELECT elementID,elementNAME,groupID FROM tbl WHERE groupID IN(2,3,7)");

$sth->exécuter();

while (my @row = $sth->fetchrow_array()) ( my $groupNAME = $dbh->selectrow_array("SELECT groupNAME FROM groups WHERE groupID = $row"); ### Disons que vous devez collecter les noms de groups ### et ajoutez-les à la fin du tableau de données push @row => $groupNAME; ### Faites autre chose... )

ou en aucun cas comme ça :

Mon $sth = $dbh->prepare("SELECT elementID,elementNAME,groupID FROM tbl WHERE groupID IN(SELECT groupID FROM groups WHERE groupNAME = "First" OR groupNAME = "Second" OR groupNAME = "Seventh")");

Si de telles actions sont nécessaires, il est préférable dans tous les cas d'utiliser un hachage, un tableau ou tout autre chemin de filtrage.

Un exemple en perl, comme je le fais habituellement :

Mes %groupes ; mon $sth = $dbh->prepare("SELECT groupID,groupNAME FROM groups WHERE groupID IN(2,3,7)"); PAR, GROUPER PAR, REJOINDRE. Ils utilisent tous des tables temporaires. Si le tri ou le regroupement est nécessaire uniquement pour afficher les éléments, par exemple par ordre alphabétique, il est préférable d'effectuer ces actions dans les variables de l'interpréteur.

Exemples Perl montrant comment ne pas trier :

Mon $sth = $dbh->prepare("SELECT elementID,elementNAME FROM tbl WHERE groupID IN(2,3,7) ORDER BY elementNAME");

$sth->exécuter();

while (my @row = $sth->fetchrow_array()) ( print qq($row => $row); )

Un exemple en Perl de la façon dont je trie habituellement : Ma $list = $dbh->selectall_arrayref("SELECT elementID,elementNAME FROM tbl WHERE groupID IN(2,3,7)"); foreach (sort ( $a-> cmp $b-> ) @$list)( print qq($_-> => $_->); )

C'est beaucoup plus rapide de cette façon. La différence est particulièrement visible s’il y a beaucoup de données. Au cas où vous auriez besoin de trier par

perl

pour plusieurs champs, vous pouvez appliquer le tri Schwartz. Si un tri aléatoire est requis ORDER BY RAND() - utilisez le tri aléatoire en Perl.

3. Utilisez des index

Bien que le tri dans la base de données puisse être abandonné dans certains cas, il est peu probable que WHERE soit possible. Par conséquent, pour les champs qui seront comparés, il est nécessaire de définir des index. Ils sont faciles à faire.

Avec cette demande :

ALTER TABLE `any_db`.`any_tbl` ADD INDEX `text_index`(`text_fld`(255));

  • Où 255 est la longueur de la clé. Pour certains types de données, cela n’est pas obligatoire. Consultez la documentation MySQL pour plus de détails.
  • La gestion des index, c'est-à-dire la manière dont ils sont créés et gérés, peut avoir un impact significatif sur les performances des requêtes SQL.
  • Très souvent, les optimisations suivantes peuvent être appliquées :
  • supprimer les index inutilisés
  • identifier les index inutilisés et inefficaces
  • améliorer les index

évitez complètement les requêtes SQL !

simplifier les requêtes SQL et options de mise en cache magique Combinaison de requêtes DDL

Les requêtes qui modifient la structure des données bloquent généralement la table. Historiquement, l'exécution

Demande ALTER nécessitait de créer une nouvelle copie de la table, ce qui peut être très long et coûteux en termes de quantité de données sur le disque. Par conséquent, au lieu de trois requêtes avec de petites modifications, il est beaucoup plus rentable d’en effectuer une seule combinée. Cela peut permettre de gagner beaucoup de temps sur les tâches d'administration de base de données., car la taille de la base de données devient physiquement importante et entraîne une augmentation du temps nécessaire à la création des sauvegardes et au temps de restauration.

Quelques conditions simples peut conduire à des index en double. Par exemple, MySQL n'a pas besoin d'index sur les champs PRIMARY.

Un index en double peut également exister si côté gauche l'un des index est complètement identique à l'autre index.

L'utilitaire pt-duplicate-key-checker de perkona-toolkit est un outil simple et moyen rapide vérifiez la structure de votre base de données pour les index inutiles.

Suppression des index inutilisés

Outre les index qui ne sont jamais utilisés car ils sont des doublons, il peut exister des index non dupliqués qui ne sont tout simplement jamais utilisés. De tels index ont le même impact que les index dupliqués. DANS MySQL standard Il n'existe aucun moyen de déterminer quels index ne sont pas utilisés, mais certaines versions disposent de cette fonctionnalité, par ex. en utilisant Google Correctif MySQL.

Ce patch a introduit une fonctionnalité : SHOW INDEX_STATISTICS.

Et dans MySQL standard, vous devez d'abord collecter toutes les requêtes SQL utilisées, les exécuter et examiner le plan d'exécution, tout en collectant des informations sur les index utilisés dans chaque cas et en les regroupant dans une seule table. En tout cas, c'est une expérience utile.

Optimisation des champs d'index.

En plus de créer de nouveaux index pour améliorer les performances, vous pouvez améliorer les performances en optimisations supplémentaires structures. Ces optimisations incluent l'utilisation de données et de types de champs personnalisés. L'avantage dans ce cas est une charge de disque inférieure et un plus grand volume d'index pouvant tenir dans la RAM.

Types de données

Certains types peuvent être remplacés sans douleur sur les bases existantes actuelles.

BIGINT contre INT

Lorsque la clé PRIMARY est définie comme BIGINT AUTO INCREMENT, il n'y a généralement aucune raison de l'utiliser. Le type de données INT UNSIGNED AUTO_INCREMENT peut stocker un nombre maximum allant jusqu'à 4294967295. Si vous avez réellement plus d'enregistrements que ce nombre, vous aurez probablement besoin d'une architecture différente.

À partir d'un tel changement de BIGINT à INT UNSIGNED, chaque ligne du tableau commence à occuper 2 fois moins d'espace sur disque, de plus, la taille occupée par la clé PRIMAIRE est réduite de 8 octets à 4.

C’est peut-être l’une des améliorations simples les plus tangibles qui puissent être réalisées sans douleur.

DATETIME et HORODATAGE

Tout est simple ici : horodatage - 4 octets, datetime - 8 octets.

Doit être utilisé autant que possible car :

  • contrôle supplémentaire de l'intégrité des données
  • un tel champ n'utilisera que 1 octet pour stocker 255 valeurs uniques
  • De tels champs sont plus pratiques à lire :)

Historiquement, l'utilisation de champs d'énumération faisait en sorte que la base dépendait des changements dans les valeurs possibles de l'énumération. Il s’agissait d’une requête DDL bloquante. À partir de Versions MySQL 5.1, l'ajout de nouvelles variantes à une énumération est très rapide et n'est pas lié à la taille de la table.

NULL vs PAS NULL

Si vous n'êtes pas sûr qu'une colonne puisse contenir une valeur nulle (NULL), il est préférable de la définir comme NOT NULL. L'index sur une telle colonne sera plus petit et plus facile à traiter.

Conversions de types automatiques

Lorsque vous sélectionnez un type de données pour joindre des champs, il peut arriver que le type de données du champ ne soit pas défini. La conversion intégrée peut représenter une surcharge totalement inutile.

Pour les champs entiers, assurez-vous que SIGNÉ et NON SIGNÉ sont identiques pour types de variables les champs, travail supplémentaire Il peut y avoir une conversion d'encodage lors de l'adhésion, alors assurez-vous de les vérifier également. Un problème courant est la conversion automatique entre les encodages latin1 et utf8.

Types de colonnes

Certains types de données sont souvent stockés dans les mauvaises colonnes. Changer le type lors de cette opération peut entraîner un stockage plus efficace, en particulier lorsque ces colonnes sont incluses dans l'index. Regardons quelques exemples typiques.

Adresse IP

L'adresse IPv4 peut être stockée dans le champ INT UNSIGNED, qui ne prend que 4 octets. Une situation courante se produit lorsque l'adresse IP est stockée dans le champ VARCHAR(15), qui occupe 12 octets. Ce seul changement peut réduire la taille de 2/3. Les fonctions INET_ATON() et INET_NTOA sont utilisées pour convertir entre une chaîne avec une adresse IP et une valeur numérique.

Pour les adresses IPv6, qui deviennent de plus en plus populaires, il est important de stocker leur valeur numérique de 128 bits dans des champs BINARY(16) et de ne pas utiliser VARCHAR pour un format lisible par l'homme.

Le stockage des champs md5 sous CHAR(32) est une pratique courante. Si vous utilisez un champ VARCHAR(32), vous ajoutez également une surcharge de longueur de chaîne supplémentaire pour chaque valeur. Cependant, une chaîne md5 est une valeur hexadécimale - et elle peut être stockée plus efficacement à l'aide des fonctions UNHEX() et HEX(). Dans ce cas, les données peuvent être stockées dans des champs BINARY(16). Cette action simple réduira la taille du champ de 32 octets à 16 octets. Un principe similaire peut être appliqué à n’importe quelle valeur hexadécimale.

Basé sur le livre de Ronald Bradford.



Des questions ?

Signaler une faute de frappe

Texte qui sera envoyé à nos rédacteurs :