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

PHP & Base de données Discussion :

Bien utiliser la fonction MERGE mysql [MySQL]


Sujet :

PHP & Base de données

  1. #1
    Membre averti
    Homme Profil pro
    Développeur Web
    Inscrit en
    Octobre 2012
    Messages
    48
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web

    Informations forums :
    Inscription : Octobre 2012
    Messages : 48
    Par défaut Bien utiliser la fonction MERGE mysql
    Bonjour,

    Je poste ce message car je viens de découvrir la fonction MERGE en Sql qui pourrait m'être utile par contre j'avoue ne pas trop comprendre à 100% comment elle fonctionne.

    Pour l'explication :
    Je fais des insertions de masse dans une base de données (des produits) quotidiennement extrait de fichier XML. Ces données doivent soit être mises à jour si elles ne sont pas présentes dans la base, soit être insérées si celles-ci sont déjà présentes dans la base. Les produits possèdent un identifiant unique en autoincrement.

    Mon code actuel n'est franchement pas optimisé et je cherche à l'améliorer au mieux pour consommer moins de mémoire et donc augmenter la vitesse de traitement.

    Code actuel :
    Code php : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
     
    <?php
    $select = mysql_query("SELECT element FROM table WHERE element='$numero_produit'");
     
    $total = mysql_num_rows($select); // Cette opération peut être répétée 25 000 fois
     
    if($total==1)
    {
    // Je procède à la mise à jour via update
    }
    else
    {
    // Sinon je procède à l'insertion avec un insert
    }
    ?>


    Le but souhaité avec Merge :
    - Supprimer l'étape mysql_num_rows
    - Gagner en temps et en mémoire.


    Ce que j'ai compris de cette instruction :
    Si la donnée a été trouvée dans la base grâce à son identifiant unique
    WHEN MATCHED -> UPDATE

    Sinon elle n'existe pas alors on l'insère
    WHEN NOT MATCHED -> INSERT

    Je comprend cette partie de l’instruction mais pas la première. Comment je pourrai mettre en place cette instruction ? C'est finalement la même que la première en PHP ci-dessus mais je pense gagner de la mémoire car au lieu d'avoir 3 instructions avec un appel php de mysql_num_rows j'en ai qu'une..

    MERGE INTO produit USING (SELECT numero_produit FROM produit WHERE numero_produit='$numero_produit' )
    WHEN MATCHED THEN UPDATE produit SET info1='$info1',info2='$info2' WHERE numero_produit='$numero_produit'
    WHEN NOT MATCHED THEN INSERT INTO produit(numero_produit,info1,info2)
    VALUES ('$numero_produit''$info1','$info2');

    Merci d'avance pour toutes explications sur MERGE !! J'ai bien cherché mais j'avoue que je pédale un peu dans la choucroute...

    Guillaume

  2. #2
    Expert confirmé Avatar de papajoker
    Homme Profil pro
    Développeur Web
    Inscrit en
    Septembre 2013
    Messages
    2 323
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nièvre (Bourgogne)

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

    Informations forums :
    Inscription : Septembre 2013
    Messages : 2 323
    Par défaut
    Bonjour,

    il existe une instruction mysql toute faite
    Code sql : Sélectionner tout - Visualiser dans une fenêtre à part
    INSERT ... ON DUPLICATE KEY UPDATE ...
    si la clé existe alors l'update est fait sinon l'insert
    il existe aussi

  3. #3
    Membre averti
    Homme Profil pro
    Développeur Web
    Inscrit en
    Octobre 2012
    Messages
    48
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web

    Informations forums :
    Inscription : Octobre 2012
    Messages : 48
    Par défaut
    Bonjour

    Merci pour le retour. Quelle fonction serait la plus rapide?

    Est il possible de specifier quelle clé est dupliqué car la duplicate key ne concerne pas ma colonne en autoincrement mais une seconde qui est reference qui est en unique key ?

    Va t il automatiquement faire la comparaison et voir que la unique key n est pas respecté?

    Vais je vraiment gagner en mémoire et temps d exécution?

    Merci

  4. #4
    Expert confirmé Avatar de papajoker
    Homme Profil pro
    Développeur Web
    Inscrit en
    Septembre 2013
    Messages
    2 323
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nièvre (Bourgogne)

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

    Informations forums :
    Inscription : Septembre 2013
    Messages : 2 323
    Par défaut
    Va chercher l'info, et tu dois faire toi même des tests de perfs en local
    http://dev.mysql.com/doc/refman/5.0/fr/insert.html
    http://dev.mysql.com/doc/refman/5.0/fr/replace.html
    Si vous spécifiez la clause ON DUPLICATE KEY UPDATE (nouveau en MySQL 4.1.0), et qu'une ligne insérée engendre un doublon pour une clé PRIMARY ou UNIQUE, une commande UPDATE sera faite à la place

    Vais je vraiment gagner en mémoire et temps d exécution?
    en mémoire ? tu crois au père noel

  5. #5
    Expert confirmé

    Homme Profil pro
    Développeur Web
    Inscrit en
    Septembre 2010
    Messages
    5 418
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Puy de Dôme (Auvergne)

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

    Informations forums :
    Inscription : Septembre 2010
    Messages : 5 418
    Par défaut
    La commande ON DUPLICATE KEY UPDATE devrait être plus rapide.

    La colonne en auto incrément je suppose que tu ne la renseigne pas dans ton insert, donc il ne devrait pas y avoir de problème.

    Il est probable que le gros de l'utilisation de ta mémoire est due à l'ouverture de ton fichier xml, donc pas de changements à ce niveau là.

    Pour le reste, côté mysql tu aurais tout intérêt à utiliser les requêtes préparées soit avec mysqli soit avec pdo. Elles sont optimisées pour les requêtes multiples.

  6. #6
    Membre averti
    Homme Profil pro
    Développeur Web
    Inscrit en
    Octobre 2012
    Messages
    48
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web

    Informations forums :
    Inscription : Octobre 2012
    Messages : 48
    Par défaut
    Pour gagner du temps j analyse le fichier xml et ensuite je procède à l insertion ou mise à jour dans une boucle. L autoincrement n est en effet pas mentionné dans mon insertion uniquement le champ en unique key

    Je viens de jeter un oeil sur les requêtes préparées et ça a l air sympa pour utiliser dans ma boucle D eexécution

    Niveau consommation de mémoire qu est ce qui serait le mieux ?? On duplicat key update ou requêtes préparées? ?

    En tout cas merci je ne connaissais pas ces fonctions :-)

  7. #7
    Expert confirmé Avatar de papajoker
    Homme Profil pro
    Développeur Web
    Inscrit en
    Septembre 2013
    Messages
    2 323
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nièvre (Bourgogne)

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

    Informations forums :
    Inscription : Septembre 2013
    Messages : 2 323
    Par défaut
    Citation Envoyé par gyllom Voir le message
    Niveau consommation de mémoire qu est ce qui serait le mieux ?? On duplicat key update ou requêtes préparées? ?
    je te le répète encore , tu ne vas rien changer au niveau consommation mémoire !
    Quelle drôle d'idée de faire l'un ou l'autre, tu désires juste optimiser à moitié ?

  8. #8
    Expert confirmé

    Homme Profil pro
    Développeur Web
    Inscrit en
    Septembre 2010
    Messages
    5 418
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Puy de Dôme (Auvergne)

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

    Informations forums :
    Inscription : Septembre 2010
    Messages : 5 418
    Par défaut
    1/ Vérifie que ton hébergeur supporte pdo (vrai dans + de 99% des cas, 100% pour les hébergeurs professionnels) si oui suis un tuto sur pdo par exemple celui-ci
    2/ Si tu ne peux pas utiliser pdo regarde un tuto sur mysqli qui supporte aussi les requêtes préparées.

    Dans tous les cas les requêtes préparées sont la voix qu'il te faut suivre : tu y gagneras en vitesse et c'est optimisé pour la gestion de la mémoire en général.
    Mais encore une fois pour diminuer sensiblement ta consommation mémoire il faudrait diminuer la taille de ton fichier xml, car c'est son chargement et traitement qui prend le plus de mémoire.

    Par ailleurs, l'extension mysql est dépréciée donc cela te fais une raison de plus pour t'intéresser à pdo. Donc bosse ce tuto (ou un autre si tu préfère) et cela te permettras de poser ensuite des questions plus pertinentes et d'être plus gourmand. Qu'est-ce que tu attends ? S'agit pas de seulement jeter un oeil, il faut savoir l'utiliser !

  9. #9
    Membre averti
    Homme Profil pro
    Développeur Web
    Inscrit en
    Octobre 2012
    Messages
    48
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web

    Informations forums :
    Inscription : Octobre 2012
    Messages : 48
    Par défaut
    Ok !

    Merci à tous les 2 pour vos réponses je vais analyser et apprendre tout ça


  10. #10
    Membre averti
    Homme Profil pro
    Développeur Web
    Inscrit en
    Octobre 2012
    Messages
    48
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web

    Informations forums :
    Inscription : Octobre 2012
    Messages : 48
    Par défaut
    Solution adoptée !! (INSERT INTO ... ON DUPLICATE KEY UPDATE)

    Mine de rien je gagne pas mal de mémoire.. une tâche qui prend normalement 1200 secondes en prends que 120 !! On peut croire au père nöel héhé !!

    Un GRAND Merci à vous

  11. #11
    Expert confirmé

    Homme Profil pro
    Développeur Web
    Inscrit en
    Septembre 2010
    Messages
    5 418
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Puy de Dôme (Auvergne)

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

    Informations forums :
    Inscription : Septembre 2010
    Messages : 5 418
    Par défaut
    Et j'espère que tu as utiliser INSERT INTO ... ON DUPLICATE KEY UPDATE dans une requête préparée correctement construite (genre faut pas mettre le prepare dans la boucle) sinon tu pourrait y gagner encore.

    A savoir aussi qu'avec php 5.4 et et MySQL >= 5.1.17 on peut (très conseillé) aussi désactiver l'émulateur de requêtes préparées de PDO pour gagner en performances.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. [WD16] Utiliser les fonctions de mysql
    Par Sannazzarotiti dans le forum WinDev
    Réponses: 8
    Dernier message: 15/06/2011, 10h28
  2. Je n'arrive pas a bien utiliser la fonction replace
    Par KawaJVC dans le forum Général JavaScript
    Réponses: 1
    Dernier message: 21/04/2008, 18h50
  3. [Syntaxe] utilisation d'une fonction dans mysql
    Par mussara dans le forum SQL Procédural
    Réponses: 2
    Dernier message: 01/04/2007, 19h40
  4. Utilisation de la fonction Merge
    Par MegaNam dans le forum Fortran
    Réponses: 2
    Dernier message: 26/03/2007, 13h49
  5. utilisation de la fonction Merge de sql
    Par freestyler dans le forum Langage SQL
    Réponses: 2
    Dernier message: 27/10/2006, 14h16

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