Précédent   Forum des professionnels en informatique > Bases de données > Oracle > SQL
SQL Forum d'entraide sur le SQL pour Oracle
Partagez cette discussion sur d'autres réseaux sociaux : Viadeo Twitter Google Facebook Digg Delicious MySpace Yahoo
Réponse Proposer ce sujet en actualité
 
Outils de la discussion
Publicité
'
Vieux 06/12/2007, 13h30   #1
Membre habitué
 
Inscription : septembre 2007
Messages : 169
Détails du profil
Informations forums :
Inscription : septembre 2007
Messages : 169
Points : 116
Points : 116
Par défaut [8i]Select particulier GROUP BY/MAX

Bonjour,
voila pas mal de temps que je butte sur une requête qui me parait pourtant relativement simple...
J'ai 3 tables : OBJET, LIVRAISON, et celle qui fait la jointure entre les 2 OBJET_LIVRAISON.

Je voudrais récupérer, pour tous les objets de OBJET, la dernière livraison correspondante(par rapport au champ "DATE" de la livraison).
Ce qui répondrait à ma requete, et qui ne marche bien entendu pas, serait quelque chose dans ce gout :
Code :
1
2
3
4
5
6
SELECT OBJET.ID_OBJET, LIVRAISON.ID_LIVRAISON
FROM OBJET, LIVRAISON, OBJET_LIVRAISON
WHERE OBJET.ID_OBJET = OBJET_LIVRAISON.ID_OBJET
AND LIVRAISON.id_livraison = OBJET_LIVRAISON.id_livraison
GROUP BY OBJET.ID_OBJET, LIVRAISON.ID_LIVRAISON
HAVING MAX("DATE") = LIVRAISON."DATE"
Voila, la réponse doit être évidente mais je ne la vois pas...
__________________
Cartes Pokémon, Yugioh, Magic ?
Communauté d'échange
kangaxx est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 14h05   #2
Rédacteur/Modérateur
 
Avatar de orafrance
 
Inscription : janvier 2004
Messages : 15 861
Détails du profil
Informations personnelles :
Âge : 35

Informations forums :
Inscription : janvier 2004
Messages : 15 861
Points : 16 212
Points : 16 212
et :

Code :
1
2
3
4
5
SELECT OBJET.ID_OBJET, LIVRAISON.ID_LIVRAISON,MAX(LIVRAISON."DATE")
FROM OBJET, LIVRAISON, OBJET_LIVRAISON
WHERE OBJET.ID_OBJET = OBJET_LIVRAISON.ID_OBJET
AND LIVRAISON.id_livraison = OBJET_LIVRAISON.id_livraison
GROUP BY OBJET.ID_OBJET, LIVRAISON.ID_LIVRAISON
orafrance est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 14h17   #3
Membre habitué
 
Inscription : septembre 2007
Messages : 169
Détails du profil
Informations forums :
Inscription : septembre 2007
Messages : 169
Points : 116
Points : 116
Merci de ta réponse, mais c'est pas encore tout à fait ca. Le problème c'est que je n'ai pas LA dernière livraison avec cette requete.
En fait ce que je peux avoir avec ta requete est :
Code :
1
2
3
ID_OBJET     ID_LIVRAISON      MAX(DATE)
12                      1                20/10/2006 15:31:39
12                      2                13/11/2006 17:45:47
Or je voudrais seulement avoir :
Code :
1
2
ID_OBJET     ID_LIVRAISON      MAX(DATE)
12                      2                13/11/2006 17:45:47
Car la derniere livraison pour l'objet '12' est la 2eme, ce que l'on sait grace à la date(a la limite j'ai pas besoin de récupérer la date apres..)
Enfin je pense il doit pas falloir changer grand chose mais décidément...
kangaxx est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 14h49   #4
Rédacteur/Modérateur
 
Avatar de orafrance
 
Inscription : janvier 2004
Messages : 15 861
Détails du profil
Informations personnelles :
Âge : 35

Informations forums :
Inscription : janvier 2004
Messages : 15 861
Points : 16 212
Points : 16 212
t'as le droit de réfléchir aussi hein

Code :
1
2
3
4
5
SELECT OBJET.ID_OBJET, MAX(LIVRAISON.ID_LIVRAISON),MAX(LIVRAISON."DATE")
FROM OBJET, LIVRAISON, OBJET_LIVRAISON
WHERE OBJET.ID_OBJET = OBJET_LIVRAISON.ID_OBJET
AND LIVRAISON.id_livraison = OBJET_LIVRAISON.id_livraison
GROUP BY OBJET.ID_OBJET
orafrance est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 14h56   #5
Expert Confirmé Sénior


 
Avatar de laurentschneider
 
Homme Laurent Schneider
Administrateur de base de données
Inscription : décembre 2005
Messages : 2 927
Détails du profil
Informations personnelles :
Nom : Homme Laurent Schneider
Localisation : Suisse

Informations professionnelles :
Activité : Administrateur de base de données
Secteur : Finance

Informations forums :
Inscription : décembre 2005
Messages : 2 927
Points : 4 549
Points : 4 549
le KEEP ça marche en 8i?

http://www.developpez.net/forums/sho...d.php?t=350923
__________________
Mon blog : laurentschneider.com
Mon livre : Advanced Oracle SQL Programming
laurentschneider est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 14h58   #6
Membre habitué
 
Inscription : septembre 2007
Messages : 169
Détails du profil
Informations forums :
Inscription : septembre 2007
Messages : 169
Points : 116
Points : 116
Oui je sais bien, mais si j'ai posté c'est parce que je ne trouve pas de solution... je cherche depuis hier, mais je dois aborder le problème par le mauvais coté.
Bon tu vas croire que je le fais expres, mais ce n'est toujours pas bon..

J'ai pensé à cette méthode, mais c'est pour cela que j'ai précisé dans mon 1er post que je devais utiliser la date de livraison pour savoir quelle est la dernière livraison, au cas où il y ait une insertion de livraison retardé pour je ne sais quelle raison. Le champ date est plus sur

Donc c'est pour ca je ne vois pas comment facilement récupérer l'id de la livraison correspondant au max de la date... En tout cas merci de ton aide.
kangaxx est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 15h03   #7
Rédacteur/Modérateur
 
Avatar de orafrance
 
Inscription : janvier 2004
Messages : 15 861
Détails du profil
Informations personnelles :
Âge : 35

Informations forums :
Inscription : janvier 2004
Messages : 15 861
Points : 16 212
Points : 16 212
donne nous les scripts de création des tables et des lignes exemples pour qu'on puisse essayer STP.

Laurent pas de fonction analytique avant la 9i
orafrance est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 15h07   #8
Rédacteur/Modérateur
 
Avatar de orafrance
 
Inscription : janvier 2004
Messages : 15 861
Détails du profil
Informations personnelles :
Âge : 35

Informations forums :
Inscription : janvier 2004
Messages : 15 861
Points : 16 212
Points : 16 212
Citation:
Envoyé par kangaxx Voir le message
Bon tu vas croire que je le fais expres, mais ce n'est toujours pas bon..
voila qui m'aide énormément pour savoir ce qui ne va pas
orafrance est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 15h19   #9
Membre habitué
 
Inscription : septembre 2007
Messages : 169
Détails du profil
Informations forums :
Inscription : septembre 2007
Messages : 169
Points : 116
Points : 116
Ok, donc voici les 3 tables :
Code :
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
CREATE TABLE OBJET
(
  ID_OBJET number
)
;
 
CREATE TABLE LIVRAISON
(
  ID_LIVRAISON number,
  "DATE" date
)
;
 
CREATE TABLE OBJET_LIVRAISON
(
  ID_OBJET number,
  ID_LIVRAISON number
)
;
Et les données, si j'ai les objets 1 et 2. Par ex
la livraison 1 livre l'objet 1 et 2 le 27-02-2006
la livraison 2 livre ce meme objet 1 le 12-06-2006
la livraison 3 livre toujours ce meme objet 1 le 10-03-2006

je voudrais avoir comme résultat :
Code :
1
2
3
ID_OBJET    ID_LIVRAISON
1               2
2               1
Citation:
voila qui m'aide énormément pour savoir ce qui ne va pas
L'explication était juste après... le problème est que tu détermine la dernière livraison avec son numéro, et j'ai précisé que je voulais le faire à partir de la date pour plus de sureté.

J'espère que mes propos sont un peu plus clairs, mais s'il reste des zones d'ombre je suis toujours la.
kangaxx est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 15h20   #10
Expert Confirmé
 
Homme
Chef de projet en SSII
Inscription : janvier 2004
Messages : 2 866
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Loire Atlantique (Pays de la Loire)

Informations professionnelles :
Activité : Chef de projet en SSII
Secteur : Conseil

Informations forums :
Inscription : janvier 2004
Messages : 2 866
Points : 3 448
Points : 3 448
Et ça :
Code :
1
2
3
4
5
SELECT OBJET.ID_OBJET, LIVRAISON.ID_LIVRAISON
FROM OBJET, LIVRAISON, OBJET_LIVRAISON
WHERE OBJET.ID_OBJET = OBJET_LIVRAISON.ID_OBJET
AND LIVRAISON.id_livraison = OBJET_LIVRAISON.id_livraison
AND LIVRAISON.DATE = (SELECT MAX(date) FROM LIVRAISON WHERE id_livraison = OBJET_LIVRAISON.id_livraison);
__________________
Un problème sans solution est un problème mal posé

Merci de poser vos questions sur le forum, je ne réponds pas aux questions posées par MP.
plaineR est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 15h36   #11
Membre habitué
 
Inscription : septembre 2007
Messages : 169
Détails du profil
Informations forums :
Inscription : septembre 2007
Messages : 169
Points : 116
Points : 116
Hélas plainer ca ne marche pas non plus, vu que je veux pour chaque objet une seule et unique installation correspondante : celle dont la date est la plus grande parmi toutes les livraisons ayant livré cet objet.
kangaxx est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 15h36   #12
Rédacteur/Modérateur
 
Avatar de orafrance
 
Inscription : janvier 2004
Messages : 15 861
Détails du profil
Informations personnelles :
Âge : 35

Informations forums :
Inscription : janvier 2004
Messages : 15 861
Points : 16 212
Points : 16 212
et ça :
Code :
1
2
3
4
5
6
7
8
9
10
SELECT ol.id_objet,
       l.id_livraison
FROM livraison l,
    (SELECT ol.id_objet,
     MAX(l."DATE") "DATE"
   FROM livraison l,
        objet_livraison ol
   WHERE l.id_livraison = ol.id_livraison
   GROUP BY ol.id_objet) ol
WHERE ol."DATE" = l."DATE"
Faut pas que 2 livraisons aient la même date par contre
orafrance est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 15h46   #13
Membre habitué
 
Inscription : septembre 2007
Messages : 169
Détails du profil
Informations forums :
Inscription : septembre 2007
Messages : 169
Points : 116
Points : 116
Oui le résultat est bon ora, par contre effectivement si 2 livraisons ont la même date, les résultats vont devenir incohérents... Normalement ca ne devrait pas arriver, vu que la date a une précision à la seconde près, mais je ne peux pas prendre le risque.
La solution "parfaite" serait de pouvoir récupérer directement le id_livraison correspondant à la max date dans la sous requete, mais pas possible...

Encore merci de m'aider à trouver une solution.
kangaxx est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 15h59   #14
Rédacteur/Modérateur
 
Avatar de orafrance
 
Inscription : janvier 2004
Messages : 15 861
Détails du profil
Informations personnelles :
Âge : 35

Informations forums :
Inscription : janvier 2004
Messages : 15 861
Points : 16 212
Points : 16 212
Citation:
Envoyé par kangaxx Voir le message
La solution "parfaite" serait de pouvoir récupérer directement le id_livraison correspondant à la max date dans la sous requete, mais pas possible...
la solution parfaite ce serait surtout un numéro d'ordre... parce qu'une sous-requête est possible mais t'aura le même problème si les dates sont égales

Le modéle ne m'a pas l'air au top
orafrance est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 16h22   #15
Expert Confirmé Sénior


 
Avatar de laurentschneider
 
Homme Laurent Schneider
Administrateur de base de données
Inscription : décembre 2005
Messages : 2 927
Détails du profil
Informations personnelles :
Nom : Homme Laurent Schneider
Localisation : Suisse

Informations professionnelles :
Activité : Administrateur de base de données
Secteur : Finance

Informations forums :
Inscription : décembre 2005
Messages : 2 927
Points : 4 549
Points : 4 549
Citation:
Envoyé par orafrance Voir le message
Laurent pas de fonction analytique avant la 9i
1) keep n'est pas une fonction analytique
2) fonctions analytiques en 8i

Bon, disons qui si keep n'existe pas, tu peux toujours employer DENSE_RANK
__________________
Mon blog : laurentschneider.com
Mon livre : Advanced Oracle SQL Programming
laurentschneider est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 16h25   #16
Expert Confirmé Sénior


 
Avatar de laurentschneider
 
Homme Laurent Schneider
Administrateur de base de données
Inscription : décembre 2005
Messages : 2 927
Détails du profil
Informations personnelles :
Nom : Homme Laurent Schneider
Localisation : Suisse

Informations professionnelles :
Activité : Administrateur de base de données
Secteur : Finance

Informations forums :
Inscription : décembre 2005
Messages : 2 927
Points : 4 549
Points : 4 549
un exemple tout prêt sorti de la doc 8i avec RANK

TOP_N
http://download-west.oracle.com/docs...ysis.htm#22773
__________________
Mon blog : laurentschneider.com
Mon livre : Advanced Oracle SQL Programming
laurentschneider est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 16h37   #17
Rédacteur/Modérateur
 
Avatar de orafrance
 
Inscription : janvier 2004
Messages : 15 861
Détails du profil
Informations personnelles :
Âge : 35

Informations forums :
Inscription : janvier 2004
Messages : 15 861
Points : 16 212
Points : 16 212
alors là ça me scie... j'étais persuadé que c'était nouveau
orafrance est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 06/12/2007, 16h52   #18
Membre habitué
 
Inscription : septembre 2007
Messages : 169
Détails du profil
Informations forums :
Inscription : septembre 2007
Messages : 169
Points : 116
Points : 116
Merci laurent, en modifiant l'exemple que tu m'as passé ca m'a l'air tout bon. Enfin ca me rassure un peu quant au fait que je n'arrivais pas à trouver la solution.. ^^

Voila la solution finale :
Code :
1
2
3
4
5
6
7
SELECT id_objet, id_livraison FROM (SELECT id_objet, l.id_livraison, RANK() OVER(PARTITION BY 
id_objet ORDER BY "DATE" DESC) AS rank1
FROM livraison l,
        objet_livraison ol
   WHERE l.id_livraison = ol.id_livraison
GROUP BY id_objet, l.id_livraison, "DATE")
WHERE rank1 <= 1;
Sinon ora, cette partie la de la base de données a été fixé, et les livraisons n'ont pas de "numéro", même si on pourrait récupérer un pseudo numéro à partir du nom de la livraison, je préférais éviter.

Edit : encore merci à vous deux, et pour votre rapidité
kangaxx est déconnecté   Envoyer un message privé Réponse avec citation 00
Réponse Proposer ce sujet en actualité Cette discussion est résolue.
Outils de la discussion



Fuseau horaire GMT +2. Il est actuellement 11h29.


 
 
 
 
Partenaires

Hébergement Web