IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Requêtes MySQL Discussion :

Index non pris en compte


Sujet :

Requêtes MySQL

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre du Club
    Profil pro
    Inscrit en
    Mars 2009
    Messages
    7
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2009
    Messages : 7
    Par défaut Index non pris en compte
    Bonjour à tous,

    Je souhaite vous faire part d'un problème que je rencontre lors de l'exécution d'une requête.

    Cette requête me génère des temps de réponses assez longues (+ de 10 sec), or mes différentes tables ne comptent pas énormément de données.

    Lorsque j'execute avec EXPLAIN la requete suivante, je constate que mes index (id_ann et xml_key) de la table PAGV5_annonces_images ne sont pas pris en compte.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    SELECT a.id_ann, a.id_reg, a.id_dep, a.id_cat, a.code_pos, a.ville, a.status, a.type, a.titre, a.ann, a.prix, a.date, o.urg, u.immediat, o.enc, i.nom AS nom_image, v.video
    	FROM PAGV5_annonces a 
    	LEFT JOIN PAGV5_annonces_options o ON a.id_ann = o.id_ann 
    	LEFT JOIN PAGV5_annonces_video v ON a.id_ann = v.id_ann
    	LEFT JOIN PAGV5_url u ON a.id_ann = u.id_ann
    	LEFT JOIN PAGV5_annonces_images i ON (a.id_ann = i.id_ann OR a.xml_key = i.xml_key) AND i.id_ima = (SELECT MIN(id_ima) FROM PAGV5_annonces_images j WHERE j.id_ann = a.id_ann OR j.xml_key = a.xml_key)
    	WHERE  etat = '2' AND a.id_dep IS NOT NULL AND a.code_pos IS NOT NULL AND type != 0 AND a.titre != '' AND a.ann != '' AND a.prix IS NOT NULL AND a.status != 0 GROUP BY u.id_ann ORDER BY a.date DESC LIMIT 0, 40;
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    id 	select_type 	table 	type 	possible_keys 	key 	key_len 	ref 	rows 	Extra
    1 	PRIMARY 	o 	system 	PRIMARY 	NULL 	NULL 	NULL 	0 	const row not found
    1 	PRIMARY 	v 	system 	id_ann 	NULL 	NULL 	NULL 	0 	const row not found
    1 	PRIMARY 	a 	ref 	search_reg,search_type,search 	search_reg 	1 	const 	180857 	Using where; Using temporary; Using filesort
    1 	PRIMARY 	u 	ref 	id_ann 	id_ann 	4 	jefouine.a.id_ann 	3 	 
    1 	PRIMARY 	i 	eq_ref 	PRIMARY,id_ann,xml_key 	PRIMARY 	4 	func 	1 	 
    2 	DEPENDENT SUBQUERY 	j 	ALL 	id_ann,xml_key 	NULL 	NULL 	NULL 	446030 	Using where
    J'ai bien tenté l'utilisation de "USE INDEX" et "FORCE INDEX" sans succès.

    Pouvez-vous m'indiquer ce qui cloche dans cette requête ?

    Merci par avance.

  2. #2
    Membre Expert
    Avatar de ericd69
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2011
    Messages
    1 919
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Isère (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Avril 2011
    Messages : 1 919
    Billets dans le blog
    1
    Par défaut
    salut,

    c'est ta sous requête j qui participe pas mal à te pourrir les perfs vu que tu extrais le min en lisant systématiquement 446030 lignes pour chaque ligne où tu l'exécutera...
    vu que tu as un or dedans tu ne pourras jamais utiliser d'index sur ces colonnes d'où la lecture systématique...
    il faut la casser en 2 avec une union et l'encadrer par un select qui refait le min des du total...
    Code sql : Sélectionner tout - Visualiser dans une fenêtre à part
    SELECT MIN(id_ima) FROM PAGV5_annonces_images j WHERE j.id_ann = a.id_ann OR j.xml_key = a.xml_key
    va devenir un truc du genre:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     select min(mini) from(
    SELECT MIN(id_ima) as mini FROM PAGV5_annonces_images j1 WHERE j1.id_ann = a.id_ann
    union
    SELECT MIN(id_ima) FROM PAGV5_annonces_images j2 WHERE  j2.xml_key = a.xml_key)
    ce qui permet à des index sur id_ann ou xml_key d’être utilisés...

    mais je pense que tu gagnerais à tenter de faire un left join sur une adaptation de cette requête avec un group by bien choisi pour ne générer ces valeur qu'une seule fois...

  3. #3
    Membre du Club
    Profil pro
    Inscrit en
    Mars 2009
    Messages
    7
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2009
    Messages : 7
    Par défaut
    Merci Eric d'avoir répondu à mon appel à l'aide

    J'ai modifié ma requête en supprimant simplement le OR.

    J'ignorais totalement qu'aucun index n'était pris en compte lorsqu'un OR étant présent dans une requête.

    Encore merci pour ton aide.

  4. #4
    Membre Expert
    Avatar de ericd69
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2011
    Messages
    1 919
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Isère (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Avril 2011
    Messages : 1 919
    Billets dans le blog
    1
    Par défaut
    résolu? si oui oublie pas de passer le post en résolu

  5. #5
    Rédacteur

    Avatar de SQLpro
    Homme Profil pro
    Expert bases de données / SQL / MS SQL Server / Postgresql
    Inscrit en
    Mai 2002
    Messages
    22 010
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Expert bases de données / SQL / MS SQL Server / Postgresql
    Secteur : Conseil

    Informations forums :
    Inscription : Mai 2002
    Messages : 22 010
    Billets dans le blog
    6
    Par défaut
    Citation Envoyé par toufika13 Voir le message
    ...
    J'ignorais totalement qu'aucun index n'était pris en compte lorsqu'un OR étant présent dans une requête.
    Ceci est dû aux faiblesses de MySQL qui est doté d'un des plus mauvais optimiseur de tous les SGBDR C/S... SQL Server ou Oracle le font très bien !

    A +
    Frédéric Brouard - SQLpro - ARCHITECTE DE DONNÉES - expert SGBDR et langage SQL
    Le site sur les SGBD relationnels et le langage SQL: http://sqlpro.developpez.com/
    Blog SQL, SQL Server, SGBDR : http://blog.developpez.com/sqlpro
    Expert Microsoft SQL Server - M.V.P. (Most valuable Professional) MS Corp.
    Entreprise SQL SPOT : modélisation, conseils, audit, optimisation, formation...
    * * * * * Expertise SQL Server : http://mssqlserver.fr/ * * * * *

  6. #6
    Membre très actif
    Profil pro
    Administrateur
    Inscrit en
    Mai 2008
    Messages
    237
    Détails du profil
    Informations personnelles :
    Localisation : Canada

    Informations professionnelles :
    Activité : Administrateur
    Secteur : Industrie

    Informations forums :
    Inscription : Mai 2008
    Messages : 237
    Par défaut
    Je pense que ton WHERE ou tes tables ont encore besoin d'être optimisé :

    Idées :
    Préférer l'usage de > ou = en lieu et place de !=
    Transformer les champs ann, etat, prix en type numérique
    Mettre des index sur tous les champs dans WHERE, ainsi que sur le champ date pourrait accélerer la requête.

    Pourquoi autant de champ NULL dans tes tables ?

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    WHERE  etat = '2' 
    AND a.id_dep IS NOT NULL 
    AND a.code_pos IS NOT NULL 
    AND type != 0 
    AND a.titre != '' 
    AND a.ann != '' 
    AND a.prix IS NOT NULL 
    AND a.STATUS != 0 
    GROUP BY u.id_ann 
    ORDER BY a.date DESC 
    LIMIT 0, 40;

Discussions similaires

  1. Z-index non pris en compte
    Par laurentSc dans le forum Mise en page CSS
    Réponses: 10
    Dernier message: 28/04/2014, 23h48
  2. Index non pris en compte
    Par Greyhunter dans le forum Administration
    Réponses: 4
    Dernier message: 11/10/2012, 18h30
  3. index.php non pris en compte
    Par Natsirt dans le forum Apache
    Réponses: 1
    Dernier message: 04/04/2011, 14h13
  4. index non pris en compte dans inner select
    Par eponette dans le forum SQL
    Réponses: 2
    Dernier message: 12/11/2007, 12h47
  5. [event] keyListener non pris en compte
    Par pierre.zelb dans le forum Agents de placement/Fenêtres
    Réponses: 5
    Dernier message: 03/08/2005, 08h35

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo