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

PL/SQL Oracle Discussion :

Dupliquer une ligne sauf un champ


Sujet :

PL/SQL Oracle

  1. #1
    Membre régulier
    Profil pro
    Inscrit en
    Juin 2004
    Messages
    136
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2004
    Messages : 136
    Points : 112
    Points
    112
    Par défaut Dupliquer une ligne sauf un champ
    Bonjour,

    je stocke dans une table un ensemble de champs dont une date début et une date fin. Je veux réaliser une procédure qui "supprime une période", c'est à dire :
    1. supprime toutes les lignes dont date début ET date fin sont comprises dans la période
    2. pour les lignes commençant avant la période, et se terminant après, il faut les scinder en deux lignes, une se terminant juste avant la période, et l'autre commençant juste après.
    3. recule la date fin de toutes les lignes se terminant dans la période
    4. avance la date début de toutes les lignes commençant dans la période

    J'exécute des delete et des update pour les points 1, 3 et 4, mais c'est le deuxième qui me pose problème. J'exécute un select pour trouver toutes les lignes répondant au critère, puis je les parcours et pour chacune, d'abord je l'update en reculant sa date de fin, puis j'insère une nouvelle ligne qui commence juste après la fin de la période.

    Si on connait parfaitement la structure de la table, pas de problème pour le select et le insert. Mais j'aimerais pouvoir utiliser cette procédure sans connaitre la structure de la table, à part en sachant qu'elle a un champ DATEDEBUT et un champ DATEFIN.

    Dans l'idéal, il me faudrait quelque chose du genre, en pseudo code :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    SELECT * FROM table WHERE datedebut < periode.debut AND dateFin > periode.fin
    FOREACH ligne
        UPDATE table SET dateFin = periode.debut
        INSERT INTO TABLE VALUES *, dateDebut = periode.fin
    END LOOP
    Bien évidemment c'est la dernière instruction que je n'arrive pas à faire. Je voudrais pouvoir dire "recopie moi la ligne à l'identique en changeant un seul champ", et je ne sais pas comment faire, à part en connaissant la structure de la table et en énumérant tous les autres champs.

    Si quelqu'un voit comment faire je suis preneur

  2. #2
    Scorpi0
    Invité(e)
    Par défaut
    Salut,

    Je voudrais pouvoir dire "recopie moi la ligne à l'identique en changeant un seul champ"
    Il suffit de le faire en 2 passes :

    - "recopie moi la ligne à l'identique" => insert into Table select * from Table where <condition>
    - "en changeant un seul champ" => update Table set maColonne = maValeur where <condition>

    Pas besoin de connaitre la structure de ta table comme ça !
    Le seul probleme est de distinguer ensuite tes lignes doublons puisque tu l'auras dupliquer. Suffit d'updater par exemple le rowid le plus grand.

  3. #3
    Membre régulier
    Profil pro
    Inscrit en
    Juin 2004
    Messages
    136
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2004
    Messages : 136
    Points : 112
    Points
    112
    Par défaut
    Merci pour ta réponse.

    le problème c'est que je ne pourrai pas dupliquer une ligne sans la changer car les deux auront la même clé (eh oui, malheureusement la base est tellement bien faite que la clé n'est pas un identifiant qu'il suffit d'incrémenter, mais un ensemble de champs :/ )

  4. #4
    Scorpi0
    Invité(e)
    Par défaut
    Ok, donc je suppose que les champs dates font parti de la clé ?
    Tu peux toujours créer une table temporaire, insérer la ligne, updater la table temporaire, insérer le contenu de ta table temporaire dans ta table principale, et dropper ta table temporaire.

    Bourrin ? un peu oui, mais au moins t'as pas a connaitre la structure de ta table ni a aller chercher dans une table system les colonnes de ta table.

  5. #5
    Membre régulier
    Profil pro
    Inscrit en
    Juin 2004
    Messages
    136
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2004
    Messages : 136
    Points : 112
    Points
    112
    Par défaut
    Oui les champs date font partie de la clé (enfin au moins un).

    J'avais pensé à la table temporaire en effet, mais c'est vrai que c'est bourrin, surtout la recréer et la dropper à chaque fois alors que ma procédure va être appelée plein de fois.

    Mais en fait tu me fais penser que je peux créer une table temporaire dans l'appelant, et la passer en paramètre, comme ça je réutilise toujours la même.

    Sinon pour aller voir dans les tables système, ce à quoi tu penses serait de récupérer la liste de tous les champs, puis construire une requête dynamique en les utilisant tous sauf dateDebut et dateFin?

  6. #6
    Scorpi0
    Invité(e)
    Par défaut
    Oui voila c'est ça.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    select column_name from USER_TAB_COLUMNS where table_name = 'MYTABLE' and column_name not in ('DT_DEB','DT_FIN')
    Tu récupères la liste des colonnes, tu construit ton insert into dynamique en PL, tadaaaa.

  7. #7
    Membre régulier
    Profil pro
    Inscrit en
    Juin 2004
    Messages
    136
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2004
    Messages : 136
    Points : 112
    Points
    112
    Par défaut
    YES j'ai trouvé une solution qui me plait

    - je déclare une variable de type tableau de MATABLE%ROWTYPE
    - je fais un select des lignes du bon intervalle dans cette variable
    - je fais un update de la date début des lignes du bon intervalle
    - je parcours mon tableau, et change la date fin de toutes ses lignes
    - je fais un forall sur mon tableau pour insérer toutes les lignes modifiées

    Et je mets l'ensemble du code dans un "execute immediate" puisque je ne connais pas ma table, et ne peux donc pas déclarer statiquement une variable de type MATABLE%ROWTYPE.

    Merci pour ton aide Scorpi0, je pense que ta dernière requête me resservira pour d'autres problèmes

  8. #8
    Scorpi0
    Invité(e)
    Par défaut
    Ah oui, j'avais oublié que le ROWTYPE existait ^^
    Bien vu

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

Discussions similaires

  1. Dupliquer une ligne
    Par Tyler Durden dans le forum SAS Base
    Réponses: 6
    Dernier message: 21/04/2010, 09h29
  2. Comment descendre d'une ligne dans un champ avec filtre automatique
    Par frolland46 dans le forum Macros et VBA Excel
    Réponses: 2
    Dernier message: 30/06/2008, 20h15
  3. Réponses: 4
    Dernier message: 26/06/2008, 12h58
  4. Ajouter une ligne dans un champs.
    Par Philippe.Girard1 dans le forum SAP Crystal Reports
    Réponses: 1
    Dernier message: 02/08/2007, 16h46
  5. Dupliquer une ligne
    Par khokho dans le forum Administration
    Réponses: 2
    Dernier message: 26/07/2007, 15h47

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