Considere o modelo relacional de uma transportadora composto...

Próximas questões
Com base no mesmo assunto
Q4375803 Banco de Dados
Considere o modelo relacional de uma transportadora composto pelas tabelas Veiculo e Viagem.
A tabela Veiculo possui as colunas CodigoVeiculo (PK) e KmAtual, contendo 50 veículos cadastrados. O atributo kmAtual aceita valores nulos.
Já a tabela Viagem possui as colunas CodigoViagem (PK), CodigoVeiculo (FK) e KmFinal, contendo os registros de viagens finalizadas.
Sabe-se que apenas 30 desses veículos possuem registros na tabela Viagem (os outros 20 são veículos recém-adquiridos que nunca viajaram).

Um desenvolvedor executou a seguinte instrução SQL no banco de dados:  

UPDATE Veiculo V
SET KmAtual =
(SELECT MAX(Vi.KmFinal)
 FROM Viagem Vi
 WHERE Vi.CodigoVeiculo = V.CodigoVeiculo
); 

Assinale a opção que descreve corretamente o resultado da execução dessa instrução. 
Alternativas

Gabarito comentado

Confira o gabarito comentado por um dos nossos professores

Gabarito: D

Fundamento decisivo: Como não há WHERE externo, os veículos sem viagens também são atualizados; MAX retorna NULL para eles, o que torna D correta.

Tema central: UPDATE com subconsulta correlacionada
Análise das alternativas
A
Errada
A proibição alegada não existe: uma subconsulta pode fornecer o valor atribuído a uma coluna em um UPDATE. Nesta instrução, o SELECT com MAX produz o valor escalar usado no SET; portanto, o uso de subconsulta não constitui o erro de sintaxe apontado.
B
Errada
Não existe a proibição geral alegada para funções de agregação nesse uso. MAX está no SELECT da subconsulta e calcula o valor que será atribuído por SET. A agregação fornece um resultado escalar, compatível com a atribuição a KmAtual.
C
Errada
O erro é afirmar que os 20 veículos sem viagens terão o valor anterior preservado. O WHERE interno seleciona as viagens utilizadas no cálculo, não os veículos sujeitos ao UPDATE. Como não há filtro externo que exclua esses veículos, eles também recebem uma atribuição: KmAtual recebe NULL, ainda que esse já fosse seu valor anterior.
D
Certa
A subconsulta é correlacionada porque usa V.CodigoVeiculo, referente ao veículo que está sendo atualizado. A condição Vi.CodigoVeiculo = V.CodigoVeiculo seleciona as viagens desse veículo, e MAX(Vi.KmFinal) fornece o maior valor não nulo encontrado. Esse resultado escalar é usado na atribuição a KmAtual. Nos veículos sem viagens, a agregação retorna NULL, e a atribuição continua sendo executada. Assim, D descreve corretamente a operação. Para os 30 veículos com viagens, a expressão “maior quilometragem” significa o resultado de MAX(KmFinal), sem garantir resultado não nulo caso não existam valores não nulos disponíveis.
E
Errada
MAX sobre um conjunto vazio retorna NULL, não zero. O UPDATE apenas atribui esse resultado à coluna; não há conversão automática para zero. Portanto, os veículos sem viagens recebem NULL em KmAtual.
Pegadinha da questão
A presença de WHERE dentro da subconsulta pode sugerir que apenas veículos com viagens serão atualizados. A confusão é tratar ausência de correspondência na consulta interna como ausência de atribuição na operação externa.
Dica para questões semelhantes
  • Ao analisar um UPDATE com subconsulta, separe duas verificações: quais linhas a instrução externa alcança e qual valor a expressão do SET produz para cada uma.
  • Ser alcançado pelo UPDATE não significa necessariamente terminar com um valor diferente: o resultado atribuído pode coincidir com o valor anterior.

Clique para visualizar este gabarito

Visualize o gabarito desta questão clicando no botão abaixo

Comentários

Veja os comentários dos nossos alunos

A opção correta é a D) Os 30 veículos que possuem registros na tabela Viagem receberão a sua maior quilometragem, enquanto os 20 restantes terão o valor de KmAtual sobrescrito como nulo (NULL).

Justificativa técnica:

* Comportamento da Subconsulta (Scalar Subquery): No padrão SQL, quando uma subconsulta escalar (que retorna uma única coluna) não encontra nenhum registro correspondente (o que ocorre para os 20 veículos que nunca viajaram), ela não falha, mas avalia o seu resultado como NULL.

* Atualização sem filtro externo (WHERE): Como a instrução UPDATE não possui uma cláusula WHERE externa (ex: WHERE EXISTS (...)), ela atualiza todos os 50 registros da tabela Veiculo:

* Para os 30 veículos com viagens, a subconsulta retorna a maior quilometragem (MAX), atualizando o campo com esse valor.

* Para os 20 veículos sem viagens, a subconsulta retorna NULL, fazendo com que o comando SET KmAtual = NULL sobrescreva o valor original desses veículos (caso tivessem algum) para NULL. (Se o objetivo fosse manter o valor original para os que não viajaram, seria necessário restringir o UPDATE com um WHERE adequado).

* Invalidação das outras opções: As opções A e B estão incorretas porque o uso de subconsultas com funções de agregação no comando SET é perfeitamente válido no padrão ANSI SQL. A opção E está incorreta porque o MAX() de um conjunto vazio retorna NULL, e não 0.

Clique para visualizar este comentário

Visualize os comentários desta questão clicando no botão abaixo