A consulta postgreSQL parece estar rodando em loop infinito

Aug 24 2020

Seguindo minha pergunta anterior , agora estou tentando remover duplicatas do meu banco de dados. Estou executando uma subconsulta para identificar os registros quase idênticos (a única diferença seria a coluna de índice "id"). Minha tabela tem cerca de 9 milhões de registros e o código abaixo teve que ser interrompido após cerca de 1h30

DELETE FROM public."OptionsData" 
WHERE id NOT IN
(
    SELECT id FROM (
        SELECT DISTINCT ON (asofdate, contract, strike, expiry, type, last, bid, ask, volume, iv, moneyness, underlying, underlyingprice) * FROM public."OptionsData"
    ) AS TempTable
);  

A produção dos resultados da subconsulta leva cerca de 1 minuto, então talvez a execução da consulta completa possa levar muito tempo (?) Ou há algo errado em meu código, por favor?

Respostas

3 a_horse_with_no_name Aug 24 2020 at 20:20

NOT IN combinado com um DISTINCT geralmente é bem lento.

Excluir duplicatas usando EXISTS é normalmente mais rápido:

DELETE FROM public."OptionsData"  d1
WHERE EXISTS (select *
              from public."OptionsData" d2
              where d1.id > d2.id
                and (d1.asofdate, d1.contract, d1.strike, d1.expiry, d1.type, d1.last, d1.bid, d1.ask, d1.volume, d1.iv, d1.moneyness, d1.underlying, d1.underlyingprice) 
                    = (d2.asofdate, d2.contract, d2.strike, d2.expiry, d2.type, d2.last, d2.bid, d2.ask, d2.volume, d2.iv, d2.moneyness, d2.underlying, d2.underlyingprice)
              )

Isso manterá as linhas com o menor valor em id. Se você quiser manter aqueles com o maior iduso where d1.id < d2.id.