9
votes

Comment sélectionner un seul enregistrement unique de la table à l'aide de distincts

Ma table a plusieurs enregistrements qui ont le même membre. Je veux résulter un seul enregistrement. XXX

Le résultat viendra. Mais je veux montrer les autres données de colonne également, mais lorsque je fais cette xxx

tous les détails, y compris les mêmes données Membres, affichant également.

Quelqu'un peut-il m'aider.


1 commentaires

Alors, comment voulez-vous choisir lequel des nombreuses lignes annuellesFees pour MemberID = 123 devraient être affichées? Ou voulez-vous juste une ligne aléatoire?


4 Réponses :


-3
votes

Sélectionnez Michaid distinct, en commençant, expiryDate, montant des fusées annuelles;

Supprimer la paranthèse


1 commentaires

Cela reviendra une rangée pour chaque permutation de Memberid, de départ, expirydate et montant



3
votes

Vous devez sélectionner laquelle des lignes avec des meubles en double pour revenir d'une manière ou d'une autre. Cela obtiendra la ligne avec le plus grand match de départ.

SELECT MemberID,StartingDate,ExpiryDate,Amount 
FROM AnnualFees af
WHERE NOT EXISTS (
        SELECT * from AnnualFees af2 
        WHERE af2.MemberID = af.MemberID 
        AND af2.StartingDate > af.StartingDate)


0 commentaires

22
votes

en supposant que vous voulez juste une ligne au hasard pour chaque membre, que vous ne pouvez le faire:

select memberid, this, that, theother
from
(
select memberid, this, that, theother,
       row_number() over (partition by memberid order by StartDate desc) rn
from   annualfees
)
where rn = 1;


4 commentaires

Re: votre dernière requête. Savez-vous si cela est plus efficace à Oracle que la version de ma réponse?


@Martin Smith: la solution analytique (Tony's) effectuera une seule passe sur les données alors que le vôtre ajoutera une jointure auto-jointure (qui peut être une petite surcharge, mais ajoutera du travail néanmoins). En général , la solution de Tony sera donc plus efficace.


@Vincent merci, je m'interrogeais sur le calcul Row_Number. Je présume que sur la seule passe, il doit créer un godet pour chaque membre, remplissez-le avec des dates de démarrage et des identifiants de ligne, puis triez chaque godet. Si oui, je peux voir que cela serait plus rapide. Si cela devinez comment cela fonctionne est totalement faux, quelqu'un faites-le moi savoir!


@Martin: Un avantage de votre solution est que Oracle n'a pas à lire toutes les lignes de Fees annuelles avant de renvoyer des lignes: il peut renvoyer des lignes car il trouve ceux qui satisfont à la clause WHERE WHERE WHERE avoir à lire toutes les lignes avant de renvoyer le premier lot. Si vous n'êtes intéressé que dans les premières lignes (et si la table est vraiment grande), vous trouverez votre requête retourne plus rapidement. (comme toujours il y a un compromis)



6
votes

Je ne sais pas si c'est tout ce dont vous avez besoin, mais vous devrez peut-être regarder le groupe en tant que distincts ...

Si vous avez plusieurs enregistrements avec le même identifiant membre, vous pourriez avoir besoin Pour spécifier Exaclty comment identifier celui que vous voulez à partir des autres strong> p>

Par exemple, pour obtenir la dernière date de début de chaque membre: strong> p>

-- show all rows
select *
from annualfees
order by memberid, startingdate
MEMBERID               STARTINGDATE              EXPIRYDATE           AMOUNT               
---------------------- ------------------------- -------------------- -------------------- 
1                      02-DEC-09                 05-FEB-10            111                  
1                      25-JUN-10                 25-JUN-11            222                  
2                      25-APR-10                 25-JUN-13            333                  

3 rows selected

/
-- show one member`s data using max(startingdate) as selector.
SELECT memberid, max(startingdate)
    FROM annualfees
    GROUP BY memberid
MEMBERID               MAX(STARTINGDATE)         
---------------------- ------------------------- 
1                      25-JUN-10                 
2                      25-APR-10                 

2 rows selected

/ 
-- show above data joined with the other columns.
SELECT subq.memid, subq.startdate, a.expirydate, a.amount
    FROM (
      SELECT memberid AS memid, max(startingdate) AS startdate
      FROM annualfees
      GROUP BY memberid ) subq
    INNER JOIN annualfees a ON a.memberid = subq.memid AND a.startingdate = subq.startdate
MEMID                  STARTDATE                 EXPIRYDATE           AMOUNT               
---------------------- ------------------------- -------------------- -------------------- 
1                      25-JUN-10                 25-JUN-11            222                  
2                      25-APR-10                 25-JUN-13            333                  

2 rows selected

/


0 commentaires