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

Delphi Discussion :

Comparaison de 2 lignes Mysql


Sujet :

Delphi

  1. #1
    Membre à l'essai
    Homme Profil pro
    Inscrit en
    Septembre 2012
    Messages
    29
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Septembre 2012
    Messages : 29
    Points : 12
    Points
    12
    Par défaut Comparaison de 2 lignes Mysql
    Bonjour, j'ai une nouvelle fois besoin de vos lumières... je possède une base de données mysql qui contient 3 champs (id, titre,numaffiche) je souhaiterais comparer les id de chaque ligne et updater le champ numaffiche en l'incrementant si le id change.
    id titre numaffiche
    OXCDE - le chant du loup -
    TRUVX - mission impossible -
    TRUVX - mission impossible -
    DDERT - avengers -

    le but étant de parcourir la table en commençant par numaffiche=1 pour le 1er et incrémenter de 1 si nouvel id en revanche si le id est identique sur 2 lignes alors ne pas incrémenter ...
    j'ai tenté de récupérer le champ id et de le mettre dans un while not x.eof le problème est qu'il me mets le chiffre 1 partout ?

    J'espère être clair et que quelqu'un pourra se pencher pour me tuyauter ?

    Merci par avance

  2. #2
    Rédacteur/Modérateur
    Avatar de Andnotor
    Inscrit en
    Septembre 2008
    Messages
    5 695
    Détails du profil
    Informations personnelles :
    Localisation : Autre

    Informations forums :
    Inscription : Septembre 2008
    Messages : 5 695
    Points : 13 133
    Points
    13 133
    Par défaut
    Ca peut se faire en SQL à l'aide de variables temporaires.
    Code sql : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    SET @LastID = '';
    SET @NumAff = 0;
     
    UPDATE table SET NumAffiche = (@NumAff := IF(ID <> @LastID, @NumAff+1, @NumAff)), ID = (@LastID := ID) ORDER BY ID;

    Avec ORDER BY la numérotation ne sera pas forcément dans l'ordre mais deux ID identiques sur des lignes non contiguës seront correctement traités.

  3. #3
    Membre à l'essai
    Homme Profil pro
    Inscrit en
    Septembre 2012
    Messages
    29
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Septembre 2012
    Messages : 29
    Points : 12
    Points
    12
    Par défaut
    Moi j'ai tenté cela mais il me voit 2 lignes puis me dit Update failed . Found 2 records... alors que ce n'est pas la fin de la table..
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    procedure TForm1.Button4Click(Sender: TObject);
    var id : string;
        j : integer;
    begin
       j:=1;
       Myupdate.SQL.Clear;
      Myupdate.SQL.Add('select * from phpoutjour order by code;');
      if not(Myupdate.Active) then Myupdate.Active:=true else Myupdate.execute;
      if myupdate.RecordCount<>0 then
      begin
        while not myupdate.Eof do
        begin
           id:=myupdate.Fields[1].Asstring;
           myupdate.Next;
          if id = (myupdate.Fields[1].asstring) then
          begin
           //pas incrementer
            myupdate.SQLUpdate.Clear;
            myupdate.SQLUpdate.Add('update phpoutjour set');
            myupdate.SQLUpdate.Add('affiche='+quotedstr(inttostr(j)));
            myupdate.SQLUpdate.Add('where id='+quotedstr(myupdate.Fields[1].asstring)+';');
             myupdate.Edit;
             myupdate.Post;
          end else
          begin
           inc(j);
           myupdate.SQLUpdate.Clear;
            myupdate.SQLUpdate.Add('update phpoutjour set');
            myupdate.SQLUpdate.Add('affiche='+quotedstr(inttostr(j)));
            myupdate.SQLUpdate.Add('where id='+quotedstr(myupdate.Fields[1].asstring)+';');
             myupdate.Edit;
             myupdate.Post;
          end;
        end;
      end;
    end;
    il me met 2 lignes à 1 et s'arrête ??

  4. #4
    Membre à l'essai
    Homme Profil pro
    Inscrit en
    Septembre 2012
    Messages
    29
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Septembre 2012
    Messages : 29
    Points : 12
    Points
    12
    Par défaut
    Citation Envoyé par didoudek Voir le message
    Moi j'ai tenté cela mais il me voit 2 lignes puis me dit Update failed . Found 2 records... alors que ce n'est pas la fin de la table..
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    procedure TForm1.Button4Click(Sender: TObject);
    var id : string;
        j : integer;
    begin
       j:=1;
       Myupdate.SQL.Clear;
      Myupdate.SQL.Add('select * from phpoutjour order by code;');
      if not(Myupdate.Active) then Myupdate.Active:=true else Myupdate.execute;
      if myupdate.RecordCount<>0 then
      begin
        while not myupdate.Eof do
        begin
           id:=myupdate.Fields[1].Asstring;
           myupdate.Next;
          if id = (myupdate.Fields[1].asstring) then
          begin
           //pas incrementer
            myupdate.SQLUpdate.Clear;
            myupdate.SQLUpdate.Add('update phpoutjour set');
            myupdate.SQLUpdate.Add('affiche='+quotedstr(inttostr(j)));
            myupdate.SQLUpdate.Add('where id='+quotedstr(myupdate.Fields[1].asstring)+';');
             myupdate.Edit;
             myupdate.Post;
          end else
          begin
           inc(j);
           myupdate.SQLUpdate.Clear;
            myupdate.SQLUpdate.Add('update phpoutjour set');
            myupdate.SQLUpdate.Add('affiche='+quotedstr(inttostr(j)));
            myupdate.SQLUpdate.Add('where id='+quotedstr(myupdate.Fields[1].asstring)+';');
             myupdate.Edit;
             myupdate.Post;
          end;
        end;
      end;
    end;
    il me met 2 lignes à 1 et s'arrête ??
    Quelqu'un peut il me dire ou se trouve l'erreur je galère depuis plusieurs jours !! Merci

  5. #5
    Expert éminent sénior
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    13 459
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Développeur C++\Delphi
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 13 459
    Points : 24 873
    Points
    24 873
    Par défaut
    Il y a une mauvaise utilisation des objets, vous devriez utiliser deux objets TQuery avec Open sur le SELECT et ExecSQL sur le UPDATE

    Le code que vous montrez n'a pas grande cohérence, vous tentez de détourner un TUpdateSQL pour lancer du SQL, ce n'est pas la bonne méthode.
    Veuillez apprendre à utiliser les objets correctement !


    Et sinon, avec un HAVING pour sélectionner les doublons et un SQL comme celui suggéré par Andnotor, tout cela se fait via un script SQL, pas besoin de Delphi
    Aide via F1 - FAQ - Guide du développeur Delphi devant un problème - Pensez-y !
    Attention Troll Méchant !
    "Quand un homme a faim, mieux vaut lui apprendre à pêcher que de lui donner un poisson" Confucius
    Mieux vaut se taire et paraître idiot, Que l'ouvrir et de le confirmer !
    L'ignorance n'excuse pas la médiocrité !

    L'expérience, c'est le nom que chacun donne à ses erreurs. (Oscar Wilde)
    Il faut avoir le courage de se tromper et d'apprendre de ses erreurs

  6. #6
    Membre à l'essai
    Homme Profil pro
    Inscrit en
    Septembre 2012
    Messages
    29
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Septembre 2012
    Messages : 29
    Points : 12
    Points
    12
    Par défaut
    Merci pour l'info mais j'utilise ce genre de requête depuis un bout de temps et cela a toujours fonctionné c'est la méthode qui ne fait pas ce que je désire... mais pouvez vous m'en dire un peu plus sur le HAVING je ne sais pas comment l'utiliser ? un petit bout de code pour la démo serait peut etre plus parlant pour un débutant ou pointer les erreurs sur mon code..
    J'utilise les composants MyDac.
    Merci à vous de vous pencher sur mon problème.

  7. #7
    Rédacteur/Modérateur

    Avatar de SergioMaster
    Homme Profil pro
    Développeur informatique retraité
    Inscrit en
    Janvier 2007
    Messages
    15 045
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 67
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique retraité
    Secteur : Industrie

    Informations forums :
    Inscription : Janvier 2007
    Messages : 15 045
    Points : 40 963
    Points
    40 963
    Billets dans le blog
    62
    Par défaut
    Bonjour,

    c'est pourtant un problème simple, dans les temps "anciens" on parlerait de rupture de contrôle

    pour le plaisir de la démonstration par code à la volée (via Firedac ne connaissant pas Mydac)

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    var Affiche: String;
         Numaffiche :integer;
    With TFDquery1.Create(Self) Do
    begin
     Connection:=TFDConnection;
     Open('SELECT id, titre, numaffiche FROM phpoutjour ORDER BY titre,numaffiche');
     Affiche:=EmptyStr;
     While not EOF do
       begin
         if affiche<>fieldByname('titre').asString then 
           begin
              affiche:=fieldByname('titre').asString;
              numAffiche:=-1;
           end;
           inc(numAffiche);
           FDConnection.ExecuteSQL('UPDATE phpoutjour SET NUMAFFICHE=? WHERE id=? AND Titre=? AND numaffiche IS NULL',
                                               [numaffiche,FieldByname('id').asString, FieldByname('titre').asString]);
          Next;   
     end;
    Bien sûr, une colonne contenant un identifiant unique autoincrémenté aurait été nettement plus utile https://dev.mysql.com/doc/refman/8.0...increment.html
    pour moi, c'est cette lacune au niveau de la structure le plus gros problème.

    Quant à la clause HAVING c'est du B.A.B.A SQL

    Code SQL : Sélectionner tout - Visualiser dans une fenêtre à part
    SELECT id, titre FROM phpoutjour GROUP BY id,titre HAVING COUNT(1)>1
    extrait tous les doublons
    MVP Embarcadero
    Delphi installés : D3,D7,D2010,XE4,XE7,D10 (Rio, Sidney), D11 (Alexandria), D12 (Athènes)
    SGBD : Firebird 2.5, 3, SQLite
    générateurs États : FastReport, Rave, QuickReport
    OS : Window Vista, Windows 10, Windows 11, Ubuntu, Androïd

  8. #8
    Rédacteur/Modérateur
    Avatar de Andnotor
    Inscrit en
    Septembre 2008
    Messages
    5 695
    Détails du profil
    Informations personnelles :
    Localisation : Autre

    Informations forums :
    Inscription : Septembre 2008
    Messages : 5 695
    Points : 13 133
    Points
    13 133
    Par défaut
    HAVING n'a pas d'intérêt puisque didoudek veut modifier toutes les lignes. AUTO_INCREMENT non plus puisque ce ne sont pas des valeurs uniques (1 id = 1 numéro).

    Quant à ton exemple Sergio et si on se réfère à la table exemple du premier poste (1 id = 1 titre), ton code va juste mettre toutes les lignes à 0.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    procedure TForm1.Button4Click(Sender: TObject);
    var
      id :string;
      j  :integer;
    begin
      j  := 0;
      id := '';
     
      myupdate.Open('select * from phpoutjour order by code;');    // A voir avec MyDac
     
      while not myupdate.Eof do
      begin
        if id <> myupdate.FiledByName('id').AsString then
        begin
          id := myupdate.FiledByName('id').AsString;
          inc(j);
        end;
     
        myupdate.Edit;
        myupdate.FiledByName('affiche').AsInteger := j;
        myupdate.Post;
     
        myupdate.Next;
      end;
    end;
    Mais c'est le besoin qui n'est pas clair ; pourquoi avoir un champ numérique qui est du 1:1 avec le champ id ?

  9. #9
    Membre à l'essai
    Homme Profil pro
    Inscrit en
    Septembre 2012
    Messages
    29
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Septembre 2012
    Messages : 29
    Points : 12
    Points
    12
    Par défaut
    Merci beaucoup Andnotor c'est toi qui a raison le code marche à merveille je me suis focalisé sur quelque chose de super compliqué en essyant de faire des comparaisons mais en fait il fallait que j'utilise le Fieldbyname...
    Merci de vos aides bien précieuses pour des débutants...

  10. #10
    Rédacteur/Modérateur

    Avatar de SergioMaster
    Homme Profil pro
    Développeur informatique retraité
    Inscrit en
    Janvier 2007
    Messages
    15 045
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 67
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique retraité
    Secteur : Industrie

    Informations forums :
    Inscription : Janvier 2007
    Messages : 15 045
    Points : 40 963
    Points
    40 963
    Billets dans le blog
    62
    Par défaut
    Bonjour,

    @AndnotOr j'ai écrit ça à l'arrache entre deux crises douloureuses (il m'a bien fallu 30 minutes pour rédiger l'ensemble !)
    contrairement à toi, je pense que non, car j'ai vu deux fois le même id (TRUVX) et titre, d'où la nécessité d'une détection de changement de titre
    pour une numérotation de 0 à 1 pour les id TRUVX
    effectivement, cependant, le fait d'utiliser un UpdateSQL avec les conditions indiquées ne peut pas fonctionner
    .. Pause douloureuse ...


    c'est pour cela que j'indiquais qu'un identifiant unique (Clé primaire ou a minima contrainete d'unicité) eut été préférable, pour éviter que le sql update soit avec cette clause WHERE id=? AND Titre=? AND numaffiche IS NULL où il manque quelque chose
    .. Pause douloureuse ...


    avec un idunique la clause where serait plus simple et de ce genre WHERE idunique=?à la réflexion tester sur id ou titre revenait au même donc il faut plutôt utiliser ID, de plus je me méfie toujours des descriptions, une majuscule, un espace, une faute d'orthographe ...

    .. Pause douloureuse ...

    Je ne sais pas si une query pour lire la table est vraiment adaptée, je me méfie des mises à jour, surtout autogénérées, sur une requête, mais, ne connaissant pas mydac, j'en reste là puisque c'est marqué résolu
    MVP Embarcadero
    Delphi installés : D3,D7,D2010,XE4,XE7,D10 (Rio, Sidney), D11 (Alexandria), D12 (Athènes)
    SGBD : Firebird 2.5, 3, SQLite
    générateurs États : FastReport, Rave, QuickReport
    OS : Window Vista, Windows 10, Windows 11, Ubuntu, Androïd

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

Discussions similaires

  1. Comparaison de 2 bases MySQL
    Par achiou59 dans le forum Administration
    Réponses: 6
    Dernier message: 31/08/2009, 15h49
  2. comparaison de fichiers LIGNE PAR LIGNE
    Par bzhbzh dans le forum Excel
    Réponses: 17
    Dernier message: 15/07/2007, 20h33
  3. Comparaison d'une ligne de caractères
    Par zennn dans le forum Débuter
    Réponses: 10
    Dernier message: 26/06/2007, 23h38
  4. Comparaison de dates dans Mysql
    Par inch dans le forum Requêtes
    Réponses: 2
    Dernier message: 05/05/2007, 12h08
  5. Comparaison de 2 lignes d'un fichier
    Par nikhun dans le forum Shell et commandes GNU
    Réponses: 1
    Dernier message: 18/10/2006, 14h00

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