Subconsultas ou Consultas Aninhadas Forma alternativa de especificar consultas envolvendo relacionamentos entre tabelas Otimização –filtragens prévias de dados na subconsulta apenas tuplas/atributos de interesse são combinados com dados da(s) tabela(s) da consulta externa Cláusulas de subconsulta –nome_atributo [NOT] IN (consulta_SQL) –nome_atributo [ | >= | | !=] ANY (consulta_SQL) –nome_atributo [ | >= | | !=] ALL (consulta_SQL)
Subconsultas com IN Testam uma relação de pertinência elemento- conjunto select lista_atributos from tabela1 [...] where atributo_ou_expressão [NOT] IN (consulta_SQL) Mapeamento para a álgebra relacional select a 1,..., a n from t 1 where c IN (select x from t 2 where d > 5) a1,..., an (t 1 X ( x ( d > 5 (t 2 )))) = t 1.c = t 2.x
Exemplos ÁlgebraSQL nome ( (Médicos X = Médicos.codm = Consultas.codm ( codm ( data = ’06/06/13’ (Consultas))) ) ) Select nome From Médicos Where codm in (select codm from Consultas where data = ‘06/06/13’) ( RG (Funcionários)) ( RG (Pacientes)) Select RG From Funcionários Where RG not in (select RG from Pacientes) ( RG (Médicos)) ( RG (Pacientes)) Select RG From Médicos Where RG in (select RG from Pacientes)
Diferença/Intersecção de Tabelas Exige tabelas compatíveis Exemplos Observação –MySQL não implementa estas operações ÁlgebraSQL relação1 relação2 consultaSQL1 except consultaSQL2 relação1 relação2 consultaSQL1 intersect consultaSQL2 ( RG (Funcionários)) ( RG (Pacientes)) Select RG From Funcionários except Select RG From Pacientes ( RG (Médicos)) ( RG (Pacientes)) Select RG From Médicos intersect Select RG From Pacientes
Subconsultas com ANY Permitem outras comparações do tipo elemento-conjunto –testam se um valor é >, <, =,... que algum valor em um conjunto select lista_atributos from tabela1 [,...] where atributo_ou_expressão [=| |>=|<>| != ] ANY (consulta_SQL) Mapeamento para a álgebra relacional select a 1,..., a n from t 1 where c > ANY (select x from t 2 where d > 5) a1,..., an (t 1 X ( x ( d > 5 (t 2 )))) = t 1.c > t 2.x
Exemplos ÁlgebraSQL nome ( (Médicos X = Médicos.codm = Consultas.codm ( codm ( data = ’06/06/13’ (Consultas))) ) ) Select nome From Médicos Where codm = any (ou in) (select codm from Consultas where data = ‘06/06/13’) Funcionários.idade ( (( idade (Funcionários)) X = Funcionários.idade < f2.idade ( idade ( f2 (Funcionários))) Select nome From Funcionários Where idade < any ( Select idade from Funcionários)
Subconsultas com ALL Realizam uma comparação de igualdade ou desigualdade de um elemento com todos os elementos de um conjunto ao mesmo tempo select lista_atributos from tabela1 [,...] where atributo_ou_expressão [=| |>=|<>| != ] ALL(consulta_SQL) Não há correspondência com a álgebra relacional –não é equivalente a divisão não filtra automaticamente atributos do dividendo na divisão, os operandos podem ter mais de um atributo na divisão existe apenas comparação de igualdade
Exemplos Select nome From Funcionários Where salário > all (Select salário From Funcionários Where departamento = ‘enfermaria’) Select nome From Funcionários Where RG all (or not in) (Select RG From Pacientes)
Comparações Elemento-Elemento Casos em que a subconsulta retorna uma única tupla como resultado –não é utilizada nenhuma cláusula de subconsulta neste caso select lista_atributos from tabela1 [,...] where atributo_ou_expressão [=| |>=|<>| != ] (consulta_SQL com um único elemento)
Exemplos Select nome From Funcionários Where salário > (Select salário From Funcionários Where RG = ) select nome, RG from Médicos where RG and especialidade = (select especialidade from Médicos where RG = )
Subconsultas com EXISTS Quantificador existencial do cálculo relacional –testa se um predicado é V ou F na subconsulta –para cada tupla da consulta externa a ser analisada, a subconsulta é executada select lista_atributos from tabela1 [,...] where [NOT] EXISTS(consulta_SQL) Mapeamento para o cálculo relacional select a 1,..., a n from T 1 where EXISTS (select * from T 2 where d > 5 and T 2.x = T 1.c) {t 1.a 1,..., t 1.a n | t 1 T 1 t 2 T 2 (t 2.d > 5 t 2.x = t 1.c) }
Exemplos CálculoSQL {m.nome | m Médicos c Consultas (c.data = ’06/06/13’ c.codm = m.codm)} Select nome From Médicos m Where exists (Select * From consultas Where data = ‘06/06/13’ and codm = m.codm) {f.nome | f Funcionários f.depto = ‘adm’ p Pacientes (p.RG = f.RG)} Select f.nome From Funcionários f Where f.depto = ‘adm’ and not exists (Select * From pacientes Where RG = f.RG)
Relembrando... t R (P(t)) t R ( P(t)) Buscar o nome dos médicos que têm consulta marcada com todos os pacientes {m.nome | m Médicos p Pacientes ( c Consultas (p.codp = c.codp c.codm = m.codm))} {m.nome | m Médicos p Pacientes ( c Consultas (p.codp = c.codp c.codm = m.codm))}
Exemplo CálculoSQL {m.nome | m Médicos p Pacientes ( c Consultas (p.codp = c.codp c.codm = m.codm))} Select nome From Médicos m Where not exists (Select * From Pacientes p Where not exists (Select * From Consultas c Where c.codp = p.codp and c.codm = m.codm))
Subconsulta na Cláusula FROM Permite a geração de uma tabela derivada a ser utilizada na consulta externa –otimização: filtra linhas e colunas de uma tabela que são desejadas pela consulta externa select lista_atributos from (consulta_SQL) as nome_tabela_derivada Mapeamento para a álgebra relacional select a 1 from (select x from t 1 where d > 5) as t 2 join t 3 on t 3.c = t 2.x a1 (t 3 X t2 ( x ( d > 5 (t 1 )))) = t 3.c = t 2.x
Exemplos ÁlgebraSQL select Medicos.*, C.hora from Medicos join (select codm, hora from Consultas where data = '06/06/13') as C on Médicos.codm = C.codm Médicos.codm,..., nroa, hora ( (Médicos X = Médicos.codm = C.codm C ( codm, hora ( data = ’06/06/13’ (Consultas))) ) ) select Amb.* from (select nroa, andar from ambulatorios) as Amb join (select nroa from Medicos where cidade = ‘Fpolis') as M_ort on Amb.nroa = M_ort.nroa Amb.nroa, andar, capacidade ( Amb ( nroa, andar (Ambulatórios)) X = Amb.nroa = M_ort.nroa M_ort ( nroa ( cidade = ’Fpolis’ (Médicos))) )