Als u een tabel met dubbele rijen in PostgreSQL heeft, kunt u een van de volgende query's gebruiken om de dubbele rijen te retourneren.
Voorbeeldgegevens
Stel dat we een tabel hebben met de volgende gegevens:
SELECT * FROM Pets;
Resultaat:
petid | petname | pettype -------+---------+--------- 1 | Wag | Dog 1 | Wag | Dog 2 | Scratch | Cat 3 | Tweet | Bird 4 | Bark | Dog 4 | Bark | Dog 4 | Bark | Dog
De eerste twee rijen zijn duplicaten en de laatste drie rijen zijn duplicaten. Dat komt omdat alle drie de kolommen dezelfde waarden bevatten in elke dubbele rij.
Optie 1
We kunnen de volgende query gebruiken om te zien hoeveel rijen duplicaten zijn:
SELECT
PetId,
PetName,
PetType,
COUNT(*) AS "Count"
FROM Pets
GROUP BY
PetId,
PetName,
PetType
ORDER BY PetId;
Resultaat:
petid | petname | pettype | Count -------+---------+---------+------- 1 | Wag | Dog | 2 2 | Scratch | Cat | 1 3 | Tweet | Bird | 1 4 | Bark | Dog | 3
We kunnen het ook sorteren op telling in aflopende volgorde, zodat de rijen met de meeste duplicaten eerst verschijnen:
SELECT
PetId,
PetName,
PetType,
COUNT(*) AS "Count"
FROM Pets
GROUP BY
PetId,
PetName,
PetType
ORDER BY Count(*) DESC;
Resultaat:
petid | petname | pettype | Count -------+---------+---------+------- 4 | Bark | Dog | 3 1 | Wag | Dog | 2 2 | Scratch | Cat | 1 3 | Tweet | Bird | 1
Optie 2
We kunnen de HAVING
. gebruiken clausule als we alleen de dubbele rijen willen hebben:
SELECT
PetId,
PetName,
PetType,
COUNT(*) AS "Count"
FROM Pets
GROUP BY
PetId,
PetName,
PetType
HAVING COUNT(*) > 1
ORDER BY PetId;
Resultaat:
petid | petname | pettype | Count -------+---------+---------+------- 1 | Wag | Dog | 2 4 | Bark | Dog | 3
Optie 3
Een andere optie is om ROW_NUMBER()
. van Postgres te gebruiken vensterfunctie:
SELECT
*,
ROW_NUMBER() OVER (
PARTITION BY PetId, PetName, PetType
ORDER BY PetId, PetName, PetType
) AS Row_Number
FROM Pets;
Resultaat:
petid | petname | pettype | row_number -------+---------+---------+------------ 1 | Wag | Dog | 1 1 | Wag | Dog | 2 2 | Scratch | Cat | 1 3 | Tweet | Bird | 1 4 | Bark | Dog | 1 4 | Bark | Dog | 2 4 | Bark | Dog | 3
De PARTITION BY
clausule verdeelt de resultaatset geproduceerd door de FROM
clausule in partities waarop de functie wordt toegepast. Wanneer we partities specificeren voor de resultatenset, zorgt elke partitie ervoor dat de nummering opnieuw begint (d.w.z. de nummering begint bij 1 voor de eerste rij in elke partitie).
Optie 4
We kunnen de bovenstaande query gebruiken als een algemene tabeluitdrukking om alleen de overtollige rijen van de overeenkomende duplicaten te retourneren:
WITH cte AS
(
SELECT
*,
ROW_NUMBER() OVER (
PARTITION BY PetId, PetName, PetType
ORDER BY PetId, PetName, PetType
) AS Row_Number
FROM Pets
)
SELECT * FROM cte WHERE Row_Number <> 1;
Resultaat:
petid | petname | pettype | row_number -------+---------+---------+------------ 1 | Wag | Dog | 2 4 | Bark | Dog | 2 4 | Bark | Dog | 3