Truc bizarre dans un EXPLAIN PLAN [ORACLE] - Programmation
Marsh Posté le 06-02-2001 à 19:45:29
Irulan >
1) c'est réellement une table ou une vue ?
2) t'as lancé plusieur fois des requêtes avant de faire l'explain plan ? (la première fois l'index n'est pas encore créé)
3) c'est sur une seule table ???
montre ta requête...
Marsh Posté le 07-02-2001 à 13:54:50
C'est une requête sur plusieurs tables.
J'avais fait un analyze table estimate statisitcs avant de la lancer, pour être sûr que l'index soit pris en compte.
Voilà la requête :
select cli.cli_id, adr.rang_adresse, adr.secteur_id, t1.cou_id,
t1.cri_id, t1.cde_specialite1, t1.typ_specialite,
adr.adr_id
from table1 t1, client cli, adresse adr
where t1.cde_specialite1=cli.cde_specialite1
and t1.cde_specialite2 is NULL
and cli.statut='Valide'
and cli.cli_id=adr.cli_id
and adr.statut='3'
and t1.cri_id=-1
--Message édité par Irulan--
Marsh Posté le 07-02-2001 à 15:24:52
Ouais. OK.
Bon, tes jointures/clés étrangères sont bien crées et indexées aussi ?
Sinon, ton index, il porte sur quel champs ?
Marsh Posté le 07-02-2001 à 15:39:16
Effectivement il faut voir en quel mode l'optimizer se trouve : COSE based ou RULE based.
En cost based, il te faut mettre à jour tes statistiques avec des :
ANALYZE TABLE <TABLE_NAME> COMPUTE STATISTICS;
et même les indexes si tes tables sont souvent updatées :
ANALYZE INDEX <INDEX_NAME> COMPUTE STATISTICS;
En effet il ne faut pas oublier que les indexes sont des structures de données et consomment de l'espace disque, au même titre qu'une table, et que ces indexes sont mis à jour à chaque update/delete dans la table indexée.
Sinon effectivement, quels champs sont indexés ?
Plusieurs champs dans un même index ou des indexes différents avec à chaque fois un champ ?
Fais attention aussi, dans te requête SQL, si utilise le 'like' avec un champ numérique, il n'utilise pas l'index mais fait un Full table scan.
Idem quand un champ est VARCHAR2 il faut utiliser 'like' dans la requête SQL et pas '=', bien que celui ci fonctionne il n'utilise pas d'index.
Marsh Posté le 07-02-2001 à 15:55:38
magicbuzz et shirley_manson > Oui il y a des index où il faut.
En fait j'essaie de comprendre un peu comment marche Oracle du point de vue utilisation des index.
Sinon la table sur laquelle Oracle effectue un Access full est utilisée en entier : j'ai lu sur un site, qu'il était plus rentable dans ce cas de ne pas mettre d'index, et de lui laisser faire un access full. Est-ce que ça pourrait être ça ?
En ce moment j'essaie un peu de comprendre l'optimisation des requêtes sous Oracle, car après cette requête on a un certain nombre de scripts qui tournent, et la dernière fois qu'on les a testés, ils ont tournés HUIT (8!) JOURS avant de cracher quelque chose.
Bon on est en test, et le serveur de prod sera plus couillu et la base plus propre, mais ça m'étonnerait que tout tienne en 2 heures comme c'était prévu à l'origine.
--Message édité par Irulan--
Marsh Posté le 07-02-2001 à 16:37:51
Irulan > En fait j'essaie de comprendre un peu comment marche Oracle du point de vue utilisation des index.
Optimisation des index ? Oracle n'optimise pas les indexes, tu peux mettre 100 indexes sur une table si ça te chante, Oracle ne se plaindra pas, c'est à toi de faire attention..
Les choses à retenir sur les indexes :
- placer des indexes sur les champs qui servent dans les clauses WHERE dans la requête SQL.
- ne pas indexes un champ vide (ça semble évident mais je l'ai vu tellement de fois sur des bases de prod).
- ne pas indexer un champ qui contient la même donnée, ça ne sert strictement à rien (si à ralentir les opérations d'écriture sur la table..)
J'ai dans la base de prod des tables énormes qui ont jusqu'à 10 indexes, mais ils sont nécessaires.
En fait il faut savoir ce qu'effectue tes scripts :
- lecture sur une table, plusieurs tables
- calculs et insert/delete dans une autre table, etc...
- archivage d'une table de prod vers une table ayant la même structure servant d'archive
à vérifier également : les valeurs PCRFREE et PCTUSED de tes tables, j'ai vu des tables qui étaient configurées pour optimiser à mort l'espace disque (en fait c'est la quantité de données qu'Oracle place dans le bloc Oracle) alors que les tables sont très utilisées en update/insert. Optimiser l'espace c'est bien, mais ça augmente considérablement les 'processing costs' comme ils le disent si bien chez Oracle..
Tu sais ce que font tes scripts ?
Marsh Posté le 07-02-2001 à 16:47:44
Je viens de relire ton post, c'est de la folie , HUIT JOURS !!
Rappelle toi qu'un index est utile à partir du moment où il 'renvoie' moins de quinze pour cent des enregistrements d'une table. En fait sur 100 enregistrements contenus dans une table, si ta requête sélectionne moins de 15 (environ, 20 ça va aussi) enregistrements alors l'index est utile.
Il faut se rappeller que l'index est mis à jour (c'est à dire que ça consomme du temps en écriture disque + cpu) à chaque mise à jour d'un enregistrement (ou de plusieurs ) d'une table..
En gros :
Mise à jour d'une table via une requête UPDATE TABLE ... WHERE ...
Oracle écrit les modifs dans la table + les indexes.
(c'est plus compliqué que ça, en fait il gère aussi avec un rollback segment le fait que tu puisses effectuer un rollback sur tes modifs, ce qui annule les modifs effectuées lors de ta transaction).
Lecture d'une table :
L'optimiseur Oracle 'étudie' la requête SQL, il regarde sur dans son cache il n'a pas la même requête qui s'y trouve déjà, crée un plan d'exécution en fonction du type d'optimisation : COST based ou RULE based. Si COST based est utilisé, il utilise les statistiques du dictionnaire de données. S'il y a utilisation d'indexes, les indexes sont lus d'abord, ENSUITE la table est accédée directement au bon endroit (adresse physique).
Il ne faut pas oublier que l'index contient l'adesse physique de la donnée indexés, donc que dès que l'index est parcouru, on tape directement dans la table au bon endroit.
Marsh Posté le 07-02-2001 à 16:52:38
Je viens de penser à un truc bête : comment sont organisés vos tablespaces ?
Vous en avez plusieurs au moins ? Y-a-t il un tablespace TEMP, ROLLBACK, un tablespace ou plus pour les indexes, un ou plusieurs pour les tables ?
La lenteur vient peut être de la contention au niveau des disques, voir les vues système V$FILESTAT pour plus d'infos.
Dans le cas évoqué plus haut (archivage d'une table dans une table archive de même structure par exemple), il peut être utile de supprimer les indexes de la table destination, de lancer le script d'archivage, puis une fois terminé de recréer les indexes.
Seul impératif, il ne faut pas de lecture sur la table d'archive pendant l'archivage vu qu'il n'y a plus d'index dessus, les requêtes seront très longues..
Désolé je suis encore plus bavard dans la vie...
Marsh Posté le 07-02-2001 à 17:17:01
shirley_manson > si tu veux on a l'habitude de gérer des alimentations de datawarehouse avec des chiffres de ventes, donc gros volumes.
Si je poste ici c'est plus par curiosité intellectuelle, et au cas où quelqu'un me donne une idée que l'on a pas déjà eu.
Pour les tablespaces, justement notre admin Oracle l'a déplacé du disque où il se trouvait initialement (ou il n'y avait plus un Mo de libre (:ouch vers un disque vide, on va voir si ça change beaucoup.
Sinon beaucoup de points que tu évoquais, nous les avons déjà vérifiés (par exemple, on drop les tables d'alimentation et on les recrée à chaque fois, puis on recrée à la fin les index qui servent dans les étapes suivantes)
Sinon les problématiques d'index, de rollback, et tout ça on maîtrîse pas trop mal donc je ne pense pas que ce soit ça.
En fait poser des index ça va, mais poser des BONS index et faire des requêtes optimisées c'est autre chose. C'est pour ça que j'essaie de creuser et de faire un peu appel à vos lumières...
--Message édité par Irulan--
Marsh Posté le 07-02-2001 à 17:19:13
Sinon quand je disais un script qi a duré 8 jours, ce n'était pas un simple update, c'est beaucoup plus complexe et il faisait appel à des procédures stockées, ce genre de truc.
Mais bon 8 jours quand même !
Marsh Posté le 07-02-2001 à 17:36:38
Irulan > Sinon les problématiques d'index, de rollback, et tout ça on maîtrîse pas trop mal donc je ne pense pas que ce soit ça.
Ok, je ne connaissais pas le niveau, je vois que vous avez un admin Oracle, que c'est du datawarehouse.
Vous travaillez avec des grosses tables, il faudrait vois si des nouveautées de la version 8 d'Oracle peuvent améliorer les choses :
- Index bitmap, peut être beaucoup plus rapide pour les requêtes sur des colonnes à faible cardinalité
- Partitionnement, pour les énormes tables, on partitionne en fonction d'un paramètre (date, status, plage de n°, etc..) et si l'optimiseur arrive à utiliser seulement une partition au lieu de la table entière il le fait.
Ces nouveautées sont dans la version Enterprise Edition de Oracle 8 il me semble..
Marsh Posté le 07-02-2001 à 17:41:21
Les bitmap on en utilise déjà pas mal donc à part en mettre partout, je ne vois pas quoi en faire de plus
Sinon le partitionnement ça m'a l'air sympa comme fonction. Comment tu fais ça ? (ou si tu as un ch'tit lien qui explique les avantages de la chose)
Marsh Posté le 07-02-2001 à 20:56:31
Un premier lien :
Partitioning Very Large Database Tables with Oracle8
http://www.oracle.com/oramag/oracle/99-Mar/29or8.html
intéressant aussi :
Tuning SQL Queries
http://www.oracle.com/oramag/oracle/00-jul/o40tun.html
Sinon je dois avoir des pdf sur les nouvelles features d'Oracle 8 au boulot (les plus intéressantes dont je me souviens sont les index bitmap et le partitionnement mais il y en a une foule d'autres.
Je regarde ça demain.
Marsh Posté le 08-02-2001 à 13:58:04
Les 'performances tips' sont sympas, et il y a pas mal de considérations sur les performances (ils sont spécialisés dans les config Unix-Oracle et le tuning).
http://www.ixora.com.au/home.htm
Marsh Posté le 06-02-2001 à 17:47:25
Est-ce que quelqu'un a déjà rencontré le truc suivant :
sous Oracle 8.0, je lance un explain plan pour voir comment la requête est gérée par Oracle.
Le coût estimé est de 4400 environ (assez gros donc).
Mais dans la description de l'explain je vois un access full sur une table.
Je pose donc un index sur cette table, je relance l'explain plan, et là ô horreur, le coût est multiplié par plus de 2 !!
Quelqu'un pourrait me dire si une raison pour laquelle Oracle multiplie par plus de 2 le coût estimé d'une requête alors qu'on lui rajoute un index (censé lui faciliter la tâche a priori?)