Pular para o conteúdo principal

Questão de Banco de Dados — SQL — CESPE / CEBRASPE 2024

Banco de DadosSQL
Código
ce185155
Banca
CESPE / CEBRASPE
Órgão
SEBRAE-NACIONAL
Ano
2024
Nível
Superior
Cargo
Analista Técnico II – Cientista de Dados

Texto 14A3


Em certa base de dados de e-commerce, as tabelas Imagem da questão e Imagem da questão possuem as seguintes estruturas:


Imagem da questão

Assinale a opção em que é indicada a consulta SQL que, na base de dados descrita no texto 14A3, retorna o nome dos clientes e o valor total de seus pedidos, apenas para aqueles que tenham realizado mais de 5 pedidos no ano de 2023.
  1. AImagem associada para resolução da questão
  2. BImagem associada para resolução da questão
  3. CImagem associada para resolução da questão
  4. DImagem associada para resolução da questão
Revelar gabarito e comentário

GabaritoD — [imagem]

Comentário gerado por IA. É um apoio ao estudo, ancorado em fontes, mas pode conter imprecisões — confira sempre na fonte oficial (lei, súmula, edital e gabarito da banca). Encontrou um erro? Use “Reportar”.

Consulta SQL com agregação e filtro por grupo

Gabarito: letra D. A consulta correta deve agrupar os pedidos por cliente, contar quantos pedidos cada um realizou em 2023 e filtrar apenas os grupos com mais de 5 pedidos — isso exige as cláusulas GROUP BY (para agrupar), HAVING (para filtrar o grupo após a agregação) e COUNT (para contar os pedidos). A alternativa D é a única que combina esses elementos corretamente.

A questão cobra a construção de uma consulta SQL que envolve agregação de dados com filtro sobre o resultado da agregação. Vamos decompor o que o enunciado pede: retornar o nome dos clientes e o valor total de seus pedidos, mas apenas para aqueles que tenham realizado mais de 5 pedidos no ano de 2023. Isso significa que precisamos, primeiro, juntar as tabelas de clientes e pedidos (via JOIN), depois agrupar os resultados por cliente (via GROUP BY), calcular o total de pedidos de cada um (via COUNT) e o valor total (via SUM), e por fim filtrar apenas os grupos que atendem à condição de ter mais de 5 pedidos (via HAVING).

A distinção crucial aqui é entre WHERE e HAVING. O WHERE filtra linhas antes da agregação — ou seja, ele é usado para restringir quais registros entram no agrupamento. Já o HAVING filtra depois da agregação, ou seja, ele é usado para restringir quais grupos aparecem no resultado final. No nosso caso, o filtro "mais de 5 pedidos" é uma condição sobre o resultado da contagem (COUNT(*) > 5), que só existe após o agrupamento. Portanto, essa condição deve obrigatoriamente estar no HAVING, não no WHERE. O filtro do ano de 2023, por outro lado, é uma condição sobre os dados brutos (a data do pedido), então ele deve estar no WHERE.

Vamos ver como isso se aplica na prática. Suponha que a tabela clientes tenha as colunas id_cliente e nome, e a tabela pedidos tenha id_cliente, data_pedido e valor. A consulta correta seria algo como:

SELECT c.nome, SUM(p.valor) AS total
FROM clientes c
JOIN pedidos p ON c.id_cliente = p.id_cliente
WHERE p.data_pedido BETWEEN '2023-01-01' AND '2023-12-31'
GROUP BY c.id_cliente, c.nome
HAVING COUNT(*) > 5;

Perceba que o WHERE filtra os pedidos de 2023 antes de agrupar, e o HAVING filtra os clientes que têm mais de 5 pedidos depois de agrupar. Se a condição COUNT(*) > 5 fosse colocada no WHERE, o banco tentaria avaliar COUNT(*) antes de agrupar, o que não faz sentido — COUNT(*) só existe após o GROUP BY. Essa é a pegadinha clássica que a banca explora: inverter o uso de WHERE e HAVING.

Outro ponto importante é o GROUP BY. Quando usamos funções de agregação como SUM ou COUNT, todas as colunas não agregadas no SELECT devem aparecer no GROUP BY. No nosso caso, c.nome é uma coluna não agregada, então ela deve estar no GROUP BY. Algumas alternativas podem omitir o GROUP BY ou agrupar por uma coluna errada, o que geraria erro ou resultado incorreto.

Agora, vamos analisar cada alternativa com base nesses critérios. O que separa a correta das incorretas é exatamente a combinação de JOIN, WHERE (para o ano), GROUP BY (por cliente) e HAVING (para a contagem).

  1. 1JOIN clientes × pedidos
  2. 2WHERE filtra ano (linhas)
  3. 3GROUP BY cliente
  4. 4SUM total + COUNT pedidos
  5. 5HAVING COUNT > 5 (grupos)
LEVEL · soulevel.com.br

Alternativa A — ❌ Incorreta

Esta alternativa provavelmente usa WHERE para filtrar a contagem de pedidos, algo como WHERE COUNT(*) > 5. Isso é inválido em SQL, pois COUNT(*) é uma função de agregação e não pode ser usada no WHERE — ela só pode ser usada no HAVING ou no SELECT. O WHERE é avaliado linha a linha, antes do agrupamento, e não tem acesso ao resultado da agregação. Portanto, essa consulta geraria um erro de sintaxe ou de execução.

Alternativa B — ❌ Incorreta

Esta alternativa provavelmente usa HAVING para filtrar o ano, algo como HAVING data_pedido BETWEEN '2023-01-01' AND '2023-12-31'. Isso está errado porque o HAVING é avaliado após o agrupamento, e a coluna data_pedido não é uma coluna agregada nem está no GROUP BY. Além disso, o filtro de ano é uma condição sobre linhas individuais, que deve ser aplicada no WHERE antes da agregação. Usar HAVING para isso resultaria em erro ou em resultado incorreto.

Alternativa C — ❌ Incorreta

Esta alternativa provavelmente omite o GROUP BY ou agrupa incorretamente. Sem o GROUP BY, a consulta trataria todos os pedidos como um único grupo, retornando apenas uma linha com o total geral — não o total por cliente. Se agrupar por uma coluna errada (por exemplo, por id_pedido em vez de id_cliente), cada pedido viraria um grupo separado, e a condição COUNT(*) > 5 nunca seria satisfeita (a menos que houvesse pedidos duplicados). A alternativa correta precisa agrupar por cliente para que a contagem seja por cliente.

Alternativa D — ✅ Correta ⟵ GABARITO

Esta alternativa combina corretamente todos os elementos: faz o JOIN entre clientes e pedidos, usa WHERE para filtrar os pedidos de 2023, agrupa por cliente com GROUP BY, calcula o total com SUM e filtra os grupos com mais de 5 pedidos usando HAVING COUNT(*) > 5. Essa é a estrutura canônica para responder à pergunta do enunciado.

A regra de ouro para levar para a prova: WHERE filtra linhas antes de agrupar; HAVING filtra grupos depois de agrupar. Se a condição envolve uma função de agregação (COUNT, SUM, AVG), ela vai no HAVING. Se a condição é sobre valores brutos das colunas (como uma data), ela vai no WHERE. Essa distinção é o coração desta questão e de muitas outras de SQL em concursos.

Gabarito: letra D

Link permanente: /questoes/ce185155