Les colonnes qui ne sont pas des index sont-elles triées sur le disque avec l'index?

8

Les colonnes qui ne sont pas des index sont-elles triées sur disque avec index, dans MySQL, dans MyISAM et InnoDB?

Une pensée incorrecte que j'ai commencé à écrire:

Je pense que non, car ils ne sont pas indexés; s'ils étaient triés, cela signifierait qu'ils sont des index.

Ce n'est pas correct parce que chaque colonne d'index est triée par ordre de son propre contenu, mais je demande à être ordonné de chaque ligne (ou seulement de certaines colonnes) avec son index correspondant.

Pour expliquer, je dis: cela serait utile pour accélérer la sélection des plages de lignes, qui se tiennent côte à côte, ensemble, par leurs index. Par exemple, si je le veux select * where id >1000 and id<2000(il peut y avoir des erreurs dans la syntaxe MySQL, je ne la connais pas bien), alors, la colonne id elle-même peut être lue rapidement à partir du disque car probablement ses cellules de 1000 à 2000 restent ensemble sur le disque physique . Mais d'autres contenus de colonnes correspondant aux identifiants 1000 à 2000 peuvent être écrits à différents endroits du disque physique. S'ils sont également triés, ils seront lus plus rapidement. Je pense que peut-être MySQL trie automatiquement ces colonnes sur le disque physique, pour les performances de telles opérations.

Sont-ils triés dans d'autres types de bases de données (PostgreSQL, etc.)?

27 décembre: je vois dans les 2 réponses que dans le cas où il y a un index cluster / clé primaire, les lignes simples elles-mêmes ne sont pas triées sur le disque physique (comme je pensais que cela pourrait / pourrait être), et même l'index cluster est non trié, s'il s'agit de b-tree, j'ai lu sur b-tree et je vois que ses nœuds, si je comprends bien, restent à des endroits aléatoires sur le disque.

qdinar
la source

Réponses:

9

Ils peuvent être triés dans certains cas. L' index de tri est généralement appelé clé de clustering . Si c'est le cas, la table entière est stockée dans un tel index (généralement dans une sorte de structure B-tree).

Dans l'autre cas, la structure de la table est connue sous le nom de tas , les lignes sont stockées telles quelles, en supprimant les feuilles "trous" dans les blocs de données et ces trous sont ensuite remplis de nouvelles lignes, de sorte que même "l'ordre d'insertion" n'est pas conservé.

MyISAM utilise la structure de tas , chaque ligne étant identifiée par l'offset (sorte d' index de tableau ) dans le fichier de données. Chaque index contient ensuite la ou les colonnes indexées pour chaque ligne, triées dans le bon ordre et avec le numéro de décalage pour localiser la ligne réelle. Cela signifie que l'accès à la ligne par n'importe quel index signifie localiser le (s) nœud (s) droit (s) dans l'index (arbre B) puis lire le (s) décalage (s) droit (s) du fichier de données (une recherche aléatoire vers une autre partie du disque peut se produire ).

InnoDB utilise le clustering par la clé primaire (ou si aucune n'est définie, la première clé unique non nulle est utilisée, ou une colonne d'auto-incrémentation interne est ajoutée - de sorte que les lignes sont toujours triées d'une manière ou d'une autre). Dans un tel cas, un accès par la clé primaire est "direct", lorsque la valeur appropriée est trouvée, vous avez une ligne entière à portée de main, pas besoin de faire une deuxième lecture. Les index secondaires, d'autre part, ne peuvent pas stocker un décalage comme dans MyISAM (car l'arbre B se rééquilibre dynamiquement, de sorte que le décalage d'une ligne spécifique peut changer à tout moment) et ils stockent les valeurs de clé primaire de la ligne à la place - donc un l'accès par une clé secondaire signifie deux recherches d'arborescence B dans InnoDB.

MS SQL Server offre une option pour rendre la clé primaire (ou un autre index) soit clusterisé ou non, vous pouvez choisir entre le tas (pas d' index est en cluster) et la structure de l' arbre (un index est en cluster). Tous les autres index non clusterisés stockent une valeur spéciale (RowID) dans le cas du segment de mémoire ou les valeurs de clé cluster de la ligne dans le cas du CI.

PostgreSQL utilise uniquement des tables de tas mais vous permet de les réorganiser par un index à la demande (vous devez le déclencher, donc les lignes sont ordonnées après l'action mais des écritures supplémentaires sur la table peuvent à nouveau casser cet ordre).

TokuDB (un moteur MySQL / MariaDB tiers) peut utiliser plusieurs clés de clustering sur une table - en fait, il conserve plusieurs copies de la table, chacune triée de manière différente. Cela vient avec une pénalité sur les écritures, mais TokuDB prétend utiliser quelque chose qu'ils appellent des index fractals, ce qui devrait rendre cette pénalité assez petite.

Si vous avez besoin d'utiliser cette fonctionnalité pour certaines requêtes, vous pouvez l '"émuler" en créant un index de couverture - de cette façon, les colonnes dont votre requête a besoin sont disponibles à tout moment dans le bon ordre, mais là encore, cela signifie maintenir une copie ordonnée de (parties de ) la table dans vos index.

jkavalik
la source
5

La réponse courte et simple pour les bases de données en général est: non, l'ordre physique des lignes dans une table n'est généralement pas le même que dans certains index de cette table.

En général (je dis en général parce qu'il y a des cas particuliers où ce n'est pas vrai) la table et l'index sont deux structures physiques différentes sur le disque. Les RDBM conventionnels stockent les données de sorte que les valeurs d'une ligne de table (et non d'une colonne ) se trouvent côte à côte sur le disque; les lignes elles-mêmes ne sont pas stockées dans un ordre particulier. Les entrées d'index, en revanche, sont stockées dans l'ordre; un index b-tree typique contient des valeurs triées de colonnes indexées (mais pas d'autres colonnes!) et une sorte de pointeur vers l'emplacement de la ligne entière dans la table qui est, comme je l'ai dit précédemment, une structure physique distincte sur le disque.

Cela étant dit, il existe des cas particuliers. Par exemple, InnoDB de MySQL stocke les lignes de données réelles dans une structure de type index. L'index par lequel les lignes sont placées dans une telle "table d'index" est généralement la clé primaire de la table; et un tel index est appelé un index clusterisé . Mais bien sûr, une table InnoDB peut avoir d'autres index et l'ordre des lignes (c'est-à-dire des colonnes de lignes incluses dans l'index respectif) dans ces index n'a rien à voir avec l'ordre des lignes dans la table elle-même.

zgguy
la source