Excluindo tuplas duplicadas no MySQL com entidades usando chaves pseudo primárias

<strong> Resumo</ Budap </p>

<a title=”Source: Flickr” target=” blank” href=” http://www.flickr.com/photos/popilop/331357312/in/photostream/”> <img height = “180” width = “240 “src =” http://farm1.static.flickr.com/128/331357312 893ef9e791 m.jpg “align =” right “/> </a> Se você tiver uma entidade onde existe uma pseudo chave primária baseada em um sequência (incremento automático) que tem duplicatas, localizar e excluir duplicatas pode ser um pouco complicado, mas veja como: </p>


<a href=” https://gist.github.com/775417″> https://gist.github.com/775417
</a>
</p>


--Make a temporary table for unneeded PKs create temporary table dirty

identificador ( número inteiro de

pseudo- chave); – Obtenha os PKs que não precisamos inserir no identificador sujo (
selecione dt1.pseudo pk da tabela suja como dt1, tabela
suja como dt2, onde dt1.true pk 1 = dt2.true pk 1
– e dt1.true
pk 2 = dt2.true pk 3
– e … continue repetindo para quantos atributos
forem sua chave real e dt1.pseudo
pk> dt2.pseudo pk
);
– Finalmente, exclua as tuplas desnecessárias da tabela suja,
exclua da
tabela suja onde o pseudo pk está (selecione pseudo pk de dirty_identifier);
</code> </pre>
<br/>

<strong> Fundo</ Budap </p>

Sem entrar muito nisso, trabalho com um banco de dados MySQL que fica sob um CMS de código fechado. O banco de dados não tem conceito de integridade referencial ou chaves naturais e usa uma sequência em cada entidade como chave primária. Uma atualização recente do fornecedor de CMS viu linhas duplicadas aparecendo. </p>

Existem três entidades em questão: o usuário, a seção e o acesso à seção. O sectionaccess contém os direitos de acesso à seção para um usuário e usa uma id de usuário e uma id de seção para fazer referência às entidades relevantes. No entanto, ele também tem um id que é usado como chave primária, ao invés de usar (sectionid, userid). Recentemente, esta entidade viu tuplas duplicadas. </p>

<strong> Detecção de duplicados </strong> </p>

Em um banco de dados lógico, as linhas distintas podem ser encontradas simplesmente usando select distinct * from sectionaccess</code>, however in this section the distinctiveness is polluted by the pseudo primary key (in this case, id).</p>To find all the tuples that are duplicates and how many of each there are we can use something like select userid, sectionid, count(*) as cnt from sectionaccess group by userid, sectionid having cnt > 1</code>. But this doesn't help us much because of the pseudo primary key.</p>What we need to do is cross reference each tuple with every other tuple in the entity on the real primary key (sectionid, userid) with a cross join. If a tuple based on the true primary key exists only once then the cross reference will occur only once and the pseudo primary key (id) will match. Where there are multiple tuples on the real primary key, the cross reference will have produce multiple tuples - some of which will have miss-matched pseudo primary keys. In my case I have assumed that the tuple with the lowest pseudo-primary key is to be kept and all the other discarded:</p>select sa1.id from sectionaccess as sa1, sectionaccess as sa2 where sa1.userid=sa2.userid and sa1.sectionid=sa2.sectionid and sa1.id > sa2.id</code></p><strong>Deleting the Duplicates</strong></p><a href="https://gist.github.com/775417">https://gist.github.com/775417</a></p>