Se você tiver uma tabela com linhas duplicadas no PostgreSQL, poderá usar qualquer uma das seguintes consultas para retornar as linhas duplicadas.
Dados de amostra
Suponha que temos uma tabela com os seguintes dados:
SELECT * FROM Pets;
Resultado:
petid | petname | pettype -------+---------+--------- 1 | Wag | Dog 1 | Wag | Dog 2 | Scratch | Cat 3 | Tweet | Bird 4 | Bark | Dog 4 | Bark | Dog 4 | Bark | Dog
As duas primeiras linhas são duplicadas e as três últimas linhas são duplicadas. Isso porque todas as três colunas contêm os mesmos valores em cada linha duplicada.
Opção 1
Podemos usar a seguinte consulta para ver quantas linhas são duplicadas:
SELECT
PetId,
PetName,
PetType,
COUNT(*) AS "Count"
FROM Pets
GROUP BY
PetId,
PetName,
PetType
ORDER BY PetId;
Resultado:
petid | petname | pettype | Count -------+---------+---------+------- 1 | Wag | Dog | 2 2 | Scratch | Cat | 1 3 | Tweet | Bird | 1 4 | Bark | Dog | 3
Alternativamente, podemos ordená-lo por contagem em ordem decrescente, para que as linhas com mais duplicatas apareçam primeiro:
SELECT
PetId,
PetName,
PetType,
COUNT(*) AS "Count"
FROM Pets
GROUP BY
PetId,
PetName,
PetType
ORDER BY Count(*) DESC;
Resultado:
petid | petname | pettype | Count -------+---------+---------+------- 4 | Bark | Dog | 3 1 | Wag | Dog | 2 2 | Scratch | Cat | 1 3 | Tweet | Bird | 1
Opção 2
Podemos usar o
HAVING
cláusula se quisermos apenas as linhas duplicadas listadas:SELECT
PetId,
PetName,
PetType,
COUNT(*) AS "Count"
FROM Pets
GROUP BY
PetId,
PetName,
PetType
HAVING COUNT(*) > 1
ORDER BY PetId;
Resultado:
petid | petname | pettype | Count -------+---------+---------+------- 1 | Wag | Dog | 2 4 | Bark | Dog | 3
Opção 3
Outra opção é usar o
ROW_NUMBER()
do Postgres função da janela:SELECT
*,
ROW_NUMBER() OVER (
PARTITION BY PetId, PetName, PetType
ORDER BY PetId, PetName, PetType
) AS Row_Number
FROM Pets;
Resultado:
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
A
PARTITION BY
cláusula divide o conjunto de resultados produzido pelo FROM
cláusula em partições às quais a função é aplicada. Quando especificamos partições para o conjunto de resultados, cada partição faz com que a numeração comece novamente (ou seja, a numeração começará em 1 para a primeira linha de cada partição). Opção 4
Podemos usar a consulta acima como uma expressão de tabela comum para retornar apenas as linhas excedentes das duplicatas correspondentes:
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;
Resultado:
petid | petname | pettype | row_number -------+---------+---------+------------ 1 | Wag | Dog | 2 4 | Bark | Dog | 2 4 | Bark | Dog | 3