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

Langage SQL Discussion :

Association des données de deux tables


Sujet :

Langage SQL

  1. #1
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2005
    Messages
    25
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2005
    Messages : 25
    Points : 18
    Points
    18
    Par défaut Association des données de deux tables
    Bonjour,

    J'ai deux tables Reglement et Taux comme ci-dessous, et je voudrais les associer pour obtenir le résultat ci-dessous (voir tout en bas).
    J'ai essayer cette requête mais ça ne fonctionne pas:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     SELECT date, sum(montant*signe), taux
    FROM reglement r, taux t
    WHERE r.date >= '01/01/2010' AND r.date <= '05/01/2010' AND t.date < r.date
    GROUP BY r.date
    Le but est de sommer les montants par date, et de leur associer le taux correspondant à la période.
    Un taux est valable pour toute la période entre la date indiquée pour le taux et la date du taux suivant.

    Quelqu'un aurait une solution svp?
    merci.

    ps: je suis sous Oracle 9i.


    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
     
    Table Reglement:
     ---------------------------------
    | date       |  montant  |  signe |
     ---------------------------------
    | 31/12/2009 | 100       |   1    |
    | 01/01/2010 | 100       |  -1    |
    | 01/01/2010 | 200       |   1    |
    | 01/01/2010 | 150       |   1    |
    | 03/01/2010 | 50        |  -1    |
    | 03/01/2010 | 10        |  -1    |
    | 04/01/2010 | 100       |  -1    |
    | 05/01/2010 | 150       |   1    |
    | 06/01/2010 |  50       |   1    |
    ----------------------------------
     
    Table Taux:
     ---------------------
    | date       |  taux  |
     ---------------------
    | 01/12/2009 | 2.5    |
    | 16/12/2009 | 3.5    |
    | 04/01/2010 | 1.5    |
     ---------------------
    Et voici ce que je veux obtenir en resultat de ma requete:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    Resultat voulu:
     ----------------------------------------
    | date       |  sum(montant*signe) |taux |
     ----------------------------------------
    | 01/01/2010 |       250           | 3.5 |
    | 03/01/2010 |       -60           | 3.5 |
    | 04/01/2010 |      -100           | 1.5 |
    | 05/01/2010 |       150           | 1.5 |
     ----------------------------------------

  2. #2
    Membre éprouvé
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    956
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 956
    Points : 1 199
    Points
    1 199
    Par défaut
    Bonjour,
    D'abord syntaxiquement ta requête était erronée car tu as oublié le taux dans le group by. De plus si tu rajoutais à la requete group by date, taux elle n'aurait pas renvoyé le bon résultat.

    Je te propose cette vilaine solution avec jointure triangulaire.
    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
    Select M.date,
    montant_signe, 
    	(	Select taux 
    		from  taux t1 where t1.date<=M.date
    		and not exists	( 	select null 
    					from taux t2 
    					where t2.date>t1.date 
    					and t2.date<=M.date
    	) taux
    from 
    (
    SELECT date, sum(montant*signe) montant_signe
    FROM reglement r
    WHERE r.date >= '01/01/2010' AND r.date <= '05/01/2010' 
    GROUP BY r.date
    ) as M
    Il y aurait une deuxième solution en créant un sous select qui te renverrait
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    ----------------------------------
    | date_debut |date fin    | taux  |
     ----------------------------------
    | 01/12/2009 | 16/12/2009 | 2.5   |
    | 16/12/2009 | 04/01/2010 |3.5    |
    | 04/01/2010 | Null       |1.5    |
    ----------------------------------
    et après tu ferais une jointure simple avec ce sous select mais je suis trop fatiguée pour l'écrire.
    Attention, si tu ne veux pas de soucis évite d'appeler tes colonnes "date".
    Cordialement
    Soazig

  3. #3
    Membre éprouvé
    Profil pro
    Inscrit en
    Octobre 2002
    Messages
    956
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2002
    Messages : 956
    Points : 1 199
    Points
    1 199
    Par défaut
    Rebonsoir,
    Le sous select renvoyant le résultat mentionné ci-dessus pourrait s'écrire:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    select T1.taux, T1.date as date_debut, 
    	select min(date) as date_fin
    	from taux T2
    	where T2.date>T1.date)
    from Taux T1
    Le résultat global ainsi
    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
    select T1.taux, T1.date as date_debut, 
    	select min(date) as date_fin
    	from taux T2
    	where T2.date>T1.date)
    from Taux T1
    SELECT M.date,
    	montant_signe, 
    	taux
    FROM 
    (
    SELECT date, sum(montant*signe) montant_signe
    FROM reglement r
    WHERE r.date >= '01/01/2010' AND r.date <= '05/01/2010' 
    GROUP BY r.date
    ) AS M
    inner join 
    (	select T1.taux, T1.date as date_debut, 
    		select min(date) as date_fin
    	from taux T2
    	where T2.date>T1.date)
    from Taux T1
    ) as T
    on M.date>=T.date_debut 
    and (T.date_fin is null or M.date<T.date_fin)
    Si la volumétrie de la table taux est largement plus faible que celle de la table reglement cette requête est préférable.

    Dans les deux cas le filtre where sur la période de date peut etre descendu hors des sous select.
    Bonne nuit
    Soazig

  4. #4
    Modérateur
    Avatar de Waldar
    Homme Profil pro
    Sr. Specialist Solutions Architect @Databricks
    Inscrit en
    Septembre 2008
    Messages
    8 453
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 46
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Sr. Specialist Solutions Architect @Databricks
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2008
    Messages : 8 453
    Points : 18 388
    Points
    18 388
    Par défaut
    J'ai plus simple avec la fonction de fenêtrage LEAD :
    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
    With Taux2 as
    (
    select dt_t as dt_t_deb,
           lead(dt_t) over(order by dt_t asc) as dt_t_fin,
           taux
      from Taux
    )
      SELECT r.dt_r, sum(r.montant * r.signe) as montant, t.taux
        FROM Reglement r
             inner join Taux2 t
               on r.dt_r >= t.dt_t_deb
              and (r.dt_r < t.dt_t_fin or t.dt_t_fin is null)
       WHERE r.dt_r between date '2010-01-01' and date '2010-01-05'
    GROUP BY r.dt_r, t.taux
    ORDER BY r.dt_r asc;
     
    DT_R                      MONTANT                TAUX                   
    ------------------------- ---------------------- ---------------------- 
    01/01/2010                250                    3,5                    
    03/01/2010                -60                    3,5                    
    04/01/2010                -100                   1,5                    
    05/01/2010                150                    1,5

Discussions similaires

  1. affichage des données de deux tables sur un état
    Par silue fignigue siaka dans le forum VB 6 et antérieur
    Réponses: 2
    Dernier message: 26/03/2009, 12h35
  2. copier des données entre deux table access (vb2005)
    Par solid_sneak06 dans le forum VB.NET
    Réponses: 9
    Dernier message: 12/07/2008, 13h20
  3. [MySQL] Fusion des données de deux tables, lors de la lecture
    Par ymoreau dans le forum PHP & Base de données
    Réponses: 2
    Dernier message: 01/06/2007, 20h45
  4. Transferer a la volée des données entre deux tables
    Par schwinny dans le forum Access
    Réponses: 2
    Dernier message: 13/07/2006, 08h50
  5. pb de relation des données de deux tables
    Par Skizo dans le forum Access
    Réponses: 3
    Dernier message: 02/06/2006, 17h00

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