sábado, 11 de dezembro de 2010

Atualizando registros através de junções de tabelas


As aplicações corporativas inserem, atualizam e excluem milhares e até milhões de registros todos os dias atavés da execução de comandos SQL na base de dados.

A atualização de registros (UPDATE) é uma tarefa normal e muito simples na maioria dos bancos de dados atuais, principalmente porque normalmente deseja-se atualizar os registros de uma única tabela.

Existem situações onde precisamos atualizar registros seguindo critérios mais elaborados, não apenas filtrando as linhas da tabela, mas também as linhas que participam de uma determinada junção entre tabelas.

Para realizar uma operação deste tipo, pode-se utilizar a seguinte sintaxe para o comando de update:

    UPDATE
        Tabela1
    SET
        campoX =  valorX
    FROM
        Tabela1 T1
    INNER JOIN Tabela2 T2 ON
        T1.id = T2.fk_id
    WHERE 
       T1.campo1 = valor1
       and T2.campo2 = valor2

Para ilustrar, vejamos um exemplo baseado na base de dados AdventureWorks2008:


No modelo acima, temos a relação dos produtos gerenciados na base com as suas categorias e sub-categorias. As tabelas Product, ProductSubCategory e ProductCategory, todas pertencentes ao Schema Production, estabelecem esta relação.

Imagine que todos as bicicletas (produtos pertencentes à categoria "Bikes") tenham sofrido um reajuste de preço 20% no preço final ao consumidor e seja necessário realizar esta atualização diretamente na base de dados.

Observe que não é possível realizar esta operação apenas adicionando filtros à cláusula WHERE, a não ser que se tenha conhecimento de cada um dos identificadores das sub-categorias da categoria "Bikes", o que seria muito trabalhoso.

Para realizar esta tarefa, utilizaremos a estrutura citada acima, unindo as 3 tabelas em questão, atualizando apenas o campo ListPrice da tabela Product dos registros cuja subcategoria pertença à categoria "Bikes".

Veja o comando a ser executado:

    UPDATE
        Production.Product
    SET
        ListPrice = ListPrice * 1.2
    FROM
        Production.Product P
    INNER JOIN Production.ProductSubcategory S ON
        P.ProductSubcategoryID = S.ProductSubcategoryID
    INNER JOIN Production.ProductCategory C ON
        S.ProductCategoryID = C.ProductCategoryID
    WHERE C.Name = 'Bikes'


Dica: Pode-se observar que a sintaxe empregada é muito parecida com a de uma consulta utilizando junções. Para evitar maiores problemas, sugerimos sempre a construção da consulta para testes dos registros afetados antes da execução da atualização desejada.

3 comentários:

Rodrigo S. Teixeira disse...

Saber utilizar esse comando facilita muito na hora de manipular diversos registros. Confesso que sem saber utilizá-lo, montava cursor do sql para fazer esse trabalho, e isso não é muito performatico. Além do update, dá pra trabalhar junções de tabelas em delete. Enfim, muito bancana o artigo....abraços

Alessandro H. Garbiati disse...

Realmente, muito util o artigo, bem explicado com exemplos e detalhes.
Estava precisando e funcionou

Robson Rogério disse...

Perfeito

Postar um comentário