Pular para o conteúdo principal

Questão de Banco de Dados — Consultas e Comandos em SQL — FGV 2024

Banco de DadosConsultas e Comandos em SQL
Código
fg165252
Banca
FGV
Órgão
TJ MS
Ano
2024
Cargo
Tec NS ( )

João, administrador de Banco de Dados experiente, percebeu que muitas consultas geradas por relatórios precisam fazer filtros pelo campo "LAST_NAME". No entanto, notou um desempenho insatisfatório devido à ausência de índices nesse campo, resultando em operações de FULL TABLE SCAN e impactando negativamente o tempo de resposta das consultas. Para resolver esse problema, ele decide identificar todas as tabelas com ausências de índices na coluna "LAST_NAME" do banco de dados, independentemente do proprietário.

 

Para isso, João deverá executar o script:

  1. ASELECT *   FROM DBA_IND_COLUMNS   WHERE COLUMN_NAME = 'LAST_NAME';
  2. BSELECT C.OWNER, C.TABLE_NAME   FROM DBA_TAB_COLUMNS C   LEFT JOIN DBA_IND_COLUMNS I ON I.TABLE_OWNER =   C.OWNER AND I.TABLE_NAME = C.TABLE_NAME AND   I.COLUMN_NAME = C.COLUMN_NAME   WHERE C.COLUMN_NAME = 'LAST_NAME' AND   I.INDEX_NAME IS NULL;
  3. CSELECT C.TABLE_NAME   FROM USER_TAB_COLUMNS C   LEFT JOIN USER_IND_COLUMNS I ON I.TABLE_NAME =   C.TABLE_NAME AND I.COLUMN_NAME = C.COLUMN_NAME   WHERE C.COLUMN_NAME = 'LAST_NAME' AND   I.INDEX_NAME IS NULL;
  4. DSELECT C.OWNER, C.TABLE_NAME   FROM ORA_COLUMNS C   LEFT JOIN ORA_IND_COLUMNS I ON I.TABLE_OWNER =   C.OWNER AND I.TABLE_NAME = C.TABLE_NAME AND   I.COLUMN_NAME = C.COLUMN_NAME   WHERE C.COLUMN_NAME = 'LAST_NAME' AND   I.INDEX_NAME IS NULL;
  5. ESELECT C.OWNER, C.TABLE_NAME   FROM DBA_TAB_COLUMNS C   LEFT JOIN DBA_IND_COLUMNS I ON I.TABLE_OWNER =   C.OWNER AND I.TABLE_NAME = C.TABLE_NAME AND   I.COLUMN_NAME = C.COLUMN_NAME   WHERE C.COLUMN_NAME = 'LAST_NAME' AND   I.INDEX_NAME IS NOT NULL;
Revelar gabarito e comentário

GabaritoB — SELECT C.OWNER, C.TABLE_NAME   FROM DBA_TAB_COLUMNS C   LEFT JOIN DBA_IND_COLUMNS I ON I.TABLE_OWNER =   C.OWNER AND I.TABLE_NAME = C.TABLE_NAME AND   I.COLUMN_NAME = C.COLUMN_NAME   WHERE C.COLUMN_NAME = 'LAST_NAME' AND   I.INDEX_NAME IS NULL;

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”.

Identificação de colunas sem índice no Oracle

Gabarito: letra B. Para identificar todas as tabelas com ausência de índices na coluna LAST_NAME, independentemente do proprietário, é necessário consultar o dicionário de dados do Oracle, combinando as visões DBA_TAB_COLUMNS (todas as colunas de todas as tabelas) e DBA_IND_COLUMNS (colunas indexadas) com um LEFT JOIN, filtrando as linhas em que a coluna da visão de índices é nula (I.INDEX_NAME IS NULL). A alternativa B é a única que atende a todos os requisitos: usa as visões DBA_* (acesso a todas as tabelas), faz o LEFT JOIN com as chaves corretas e filtra corretamente a ausência de índice.

O problema descrito é clássico em administração de bancos de dados Oracle: identificar colunas que não possuem índices para otimizar consultas. O dicionário de dados do Oracle armazena metadados sobre todos os objetos do banco, incluindo tabelas, colunas e índices. As visões do dicionário são a fonte oficial para esse tipo de consulta administrativa.

Existem três níveis de visões no Oracle, que variam conforme o escopo de acesso:

  • USER_*: mostra apenas os objetos pertencentes ao usuário atual.

  • ALL_*: mostra os objetos que o usuário atual tem permissão de acessar.

  • DBA_*: mostra todos os objetos do banco, independentemente do proprietário (requer privilégios de DBA).

Como o enunciado pede "independentemente do proprietário", a consulta deve usar as visões DBA_*. Isso elimina a alternativa C, que usa USER_TAB_COLUMNS e USER_IND_COLUMNS, restringindo o resultado ao esquema do usuário atual.

A lógica da consulta é:

  1. DBA_TAB_COLUMNS (aliás C): contém todas as colunas de todas as tabelas do banco.

  2. DBA_IND_COLUMNS (aliás I): contém as colunas que participam de índices.

  3. LEFT JOIN: preserva todas as linhas da tabela à esquerda (C), mesmo que não haja correspondência em I. Quando não há índice para a coluna, os campos de I ficam nulos.

  4. Filtro I.INDEX_NAME IS NULL: seleciona apenas as linhas em que não houve correspondência, ou seja, colunas sem índice.

A alternativa B aplica exatamente essa lógica, com as chaves de junção corretas: TABLE_OWNER, TABLE_NAME e COLUMN_NAME. O LEFT JOIN é essencial: se fosse um INNER JOIN, apenas colunas com índice seriam retornadas, e o filtro IS NULL nunca seria verdadeiro.

A alternativa E usa o mesmo LEFT JOIN, mas filtra I.INDEX_NAME IS NOT NULL, o que retornaria apenas colunas que possuem índice — exatamente o oposto do desejado.

A alternativa A apenas seleciona todas as colunas indexadas com nome LAST_NAME, sem identificar as que não possuem índice.

A alternativa D usa visões ORA_COLUMNS e ORA_IND_COLUMNS, que não existem no dicionário de dados do Oracle. As visões corretas são DBA_TAB_COLUMNS e DBA_IND_COLUMNS.

Portanto, a alternativa B é a única que atende plenamente ao requisito: identificar todas as tabelas com ausência de índices na coluna LAST_NAME, independentemente do proprietário.

1USER_*
Objetos do usuário atual
2ALL_*
Objetos acessíveis ao usuário
3DBA_*
Todos os objetos do banco
Independente do proprietário
4Padrão para achar ausência
LEFT JOIN (tabela da esquerda preservada)
Filtro IS NULL na chave da direita
Ex.: colunas sem índice
Visões do dicionário Oracle
LEVELsoulevel.com.br
Visões do dicionário Oracle: USER_* (Objetos do usuário atual); ALL_* (Objetos acessíveis ao usuário); DBA_* (Todos os objetos do banco, Independente do proprietário); Padrão para achar ausência (LEFT JOIN (tabela da esquerda preservada), Filtro IS NULL na chave da direita, Ex.: colunas sem índice)

Alternativa A — ❌ Incorreta

Esta consulta apenas retorna todas as colunas indexadas com nome LAST_NAME a partir de DBA_IND_COLUMNS. Ela não identifica colunas sem índice; pelo contrário, lista justamente as que possuem índice. O requisito é encontrar as que não possuem, então esta alternativa falha completamente.

Alternativa B — ✅ Correta ⟵ GABARITO

Esta é a consulta correta. Ela:

  • Usa DBA_TAB_COLUMNS e DBA_IND_COLUMNS, que cobrem todas as tabelas do banco, independentemente do proprietário.

  • Faz LEFT JOIN com as chaves corretas (TABLE_OWNER, TABLE_NAME, COLUMN_NAME), preservando todas as colunas.

  • Filtra I.INDEX_NAME IS NULL, selecionando apenas as colunas que não possuem índice correspondente.

  • Retorna OWNER e TABLE_NAME, identificando claramente cada tabela.

Alternativa C — ❌ Incorreta

Usa as visões USER_TAB_COLUMNS e USER_IND_COLUMNS, que restringem o resultado ao esquema do usuário atual. O enunciado exige "independentemente do proprietário", portanto as visões DBA_* são obrigatórias. Além disso, não retorna o OWNER, o que dificultaria a identificação completa da tabela.

Alternativa D — ❌ Incorreta

As visões ORA_COLUMNS e ORA_IND_COLUMNS não existem no dicionário de dados do Oracle. As visões corretas são DBA_TAB_COLUMNS e DBA_IND_COLUMNS. Portanto, a consulta falharia com erro de objeto não encontrado.

Alternativa E — ❌ Incorreta

Embora use as visões DBA_* e o LEFT JOIN corretamente, o filtro I.INDEX_NAME IS NOT NULL seleciona apenas as colunas que possuem índice. O requisito é identificar as que não possuem, então o filtro deveria ser IS NULL. Esta alternativa retorna exatamente o oposto do desejado.

NÃO CAIA NESSA!

A banca explora a confusão entre IS NULL e IS NOT NULL no filtro após o LEFT JOIN. Muitos candidatos invertem o filtro, retornando colunas com índice em vez de sem índice. Lembre-se: no LEFT JOIN, as linhas sem correspondência têm os campos da tabela da direita nulos; para encontrar ausência, use IS NULL.

PEGA ESSA DICA!

Para questões de dicionário de dados no Oracle, memorize a diferença entre USER_*, ALL_* e DBA_*. Quando o enunciado pedir "independentemente do proprietário" ou "todas as tabelas", use DBA_*. E para identificar ausência de relacionamento, o padrão é LEFT JOIN + IS NULL na chave da tabela da direita.

Gabarito: letra B

Link permanente: /questoes/fg165252