Comment trouver des valeurs en double dans une table dans Oracle?

277

Quelle est l'instruction SQL la plus simple qui retournera les valeurs en double pour une colonne donnée et le nombre de leurs occurrences dans une table de base de données Oracle?

Par exemple: j'ai une JOBStable avec la colonne JOB_NUMBER. Comment savoir si j'ai des doublons JOB_NUMBERet combien de fois ils sont dupliqués?

Andrew
la source
1
autres solutions stackoverflow.com/questions/4522431/…
zloctb

Réponses:

610
SELECT column_name, COUNT(column_name)
FROM table_name
GROUP BY column_name
HAVING COUNT(column_name) > 1;
Bill le lézard
la source
1
Merci - c'est la réponse que je viens de trouver et vous m'avez battu pour la publier ici! : o)
Andrew
3
De rien. Maintenant, je suis sur le point de poster ma propre question sur les différences entre le nombre (colonne) et le nombre (*). :)
Bill the Lizard
44
+1 sur 4 ans plus tard, fonctionne toujours bien et peut être ajusté pour sélectionner plusieurs colonnes tant que celles-ci sont également dans le group by, comme dans: select column_one, column_two, count(*) from tablename group by column_one, column_two having count(column_one) > 1;etc.
Amos M. Carpenter
4
ou même having count(*) > 1: D
Stanislav Mamontov
3
+1 sur 8 ans plus tard, fonctionne toujours bien pour les deux dernières versions d'Oracle et MySQL (supprimer l'espace après la fonction de comptage en ayant une ligne).
PhatHV
58

Autrement:

SELECT *
FROM TABLE A
WHERE EXISTS (
  SELECT 1 FROM TABLE
  WHERE COLUMN_NAME = A.COLUMN_NAME
  AND ROWID < A.ROWID
)

Fonctionne bien (assez rapidement) quand l'index est activé column_name. Et c'est une meilleure façon de supprimer ou de mettre à jour les lignes en double.

Gris
la source
3
+1 fonctionne bien pour les doublons multi-colonnes (par exemple, lorsque vous souhaitez ajouter une contrainte UNIQUE sur plusieurs colonnes), j'ai trouvé cette approche moins "rigide" que la GROUP BY pour lister les valeurs des champs en double + d'autres champs si nécessaire.
Frosty Z
3
Juste pour clarifier, (ce n'était pas évident pour moi au début), cette requête ne renvoie que les doublons, elle ne renvoie pas la première entrée d'origine, c'est pourquoi elle fonctionne bien pour supprimer les doublons, basée sur une contrainte unique sur plus de 1 colonne. Vous pouvez sélectionner les ID en double avec cette requête, puis les utiliser pour supprimer les doublons.
matthewb
1
si vous changez <en! = vous obtiendrez tous les enregistrements qui se dupliquent. pas seulement le 2e ou le 3e record
moore1emu
33

Le plus simple que je puisse penser:

select job_number, count(*)
from jobs
group by job_number
having count(*) > 1;
JosephStyons
la source
1
Comment puis-je obtenir toutes les colonnes?
Asif Mushtaq
2
sélectionnez * à partir des travaux où numéro_travail (sélectionnez numéro_travail à partir du groupe de travaux par numéro_travail ayant un décompte (*)> 1)
JosephStyons
17

Vous n'avez même pas besoin d'avoir le nombre dans les colonnes renvoyées si vous n'avez pas besoin de connaître le nombre réel de doublons. par exemple

SELECT column_name
FROM table
GROUP BY column_name
HAVING COUNT(*) > 1
Evan
la source
7

Que diriez-vous:

SELECT <column>, count(*)
FROM <table>
GROUP BY <column> HAVING COUNT(*) > 1;

Pour répondre à l'exemple ci-dessus, cela ressemblerait à:

SELECT job_number, count(*)
FROM jobs
GROUP BY job_number HAVING COUNT(*) > 1;
Andrew
la source
5

Dans le cas où plusieurs colonnes identifient une ligne unique (par exemple une table de relations), vous pouvez utiliser les éléments suivants

Utilisez l'identifiant de ligne, par exemple emp_dept (empid, deptid, startdate, enddate) supposons que empid et deptid sont uniques et identifient la ligne dans ce cas

select oed.empid, count(oed.empid) 
from emp_dept oed 
where exists ( select * 
               from  emp_dept ied 
                where oed.rowid <> ied.rowid and 
                       ied.empid = oed.empid and 
                      ied.deptid = oed.deptid )  
        group by oed.empid having count(oed.empid) > 1 order by count(oed.empid);

et si une telle table a une clé primaire, utilisez la clé primaire au lieu de rowid, par exemple id est pk alors

select oed.empid, count(oed.empid) 
from emp_dept oed 
where exists ( select * 
               from  emp_dept ied 
                where oed.id <> ied.id and 
                       ied.empid = oed.empid and 
                      ied.deptid = oed.deptid )  
        group by oed.empid having count(oed.empid) > 1 order by count(oed.empid);
Jitendra Vispute
la source
4

Faire

select count(j1.job_number), j1.job_number, j1.id, j2.id
from   jobs j1 join jobs j2 on (j1.job_numer = j2.job_number)
where  j1.id != j2.id
group by j1.job_number

vous donnera les identifiants des lignes dupliquées.

agnul
la source
4
SELECT   SocialSecurity_Number, Count(*) no_of_rows
FROM     SocialSecurity 
GROUP BY SocialSecurity_Number
HAVING   Count(*) > 1
Order by Count(*) desc 
Wahid Haidari
la source
2

Je l'habitude d' utiliser Oracle analytique fonction ROW_NUMBER () .

Dites que vous voulez vérifier les doublons que vous avez concernant un index unique ou une clé primaire construite sur des colonnes ( c1, c2, c3). Ensuite, vous irez de cette façon, en faisant apparaître des ROWIDs de lignes où le nombre de lignes apportées ROW_NUMBER()est >1:

Select * From Table_With_Duplicates
      Where Rowid In
                    (Select Rowid
                       From (Select Rowid,
                                    ROW_NUMBER() Over (
                                            Partition By c1 || c2 || c3
                                            Order By c1 || c2 || c3
                                        ) nbLines
                               From Table_With_Duplicates) t2
                      Where nbLines > 1)
J. Chomel
la source
1

Voici une requête SQL pour ce faire:

select column_name, count(1)
from table
group by column_name
having count (column_name) > 1;
Chaminda Dilshan
la source
1

Je sais que c'est un vieux fil mais cela peut aider quelqu'un.

Si vous avez besoin d'imprimer d'autres colonnes du tableau tout en vérifiant l'utilisation en double ci-dessous:

select * from table where column_name in
(select ing.column_name from table ing group by ing.column_name having count(*) > 1)
order by column_name desc;

peut également ajouter des filtres supplémentaires dans la clause where si nécessaire.

Parth Kansara
la source
0

1. solution

select * from emp
    where rowid not in
    (select max(rowid) from emp group by empno);
Fais ou meurs
la source
Cette affiche originale n'a jamais mentionné la suppression, ne comptant que
Jeff
-1

Vous pouvez également essayer quelque chose comme ça pour répertorier toutes les valeurs en double dans une table, dites reqitem

SELECT count(poid) 
FROM poitem 
WHERE poid = 50 
AND rownum < any (SELECT count(*)  FROM poitem WHERE poid = 50) 
GROUP BY poid 
MINUS
SELECT count(poid) 
FROM poitem 
WHERE poid in (50)
GROUP BY poid 
HAVING count(poid) > 1;
Empileur
la source