Documentos de Académico
Documentos de Profesional
Documentos de Cultura
Ejercicios SQL
Ejercicios SQL
FACULTAD DE INGENIERÍA
1
Introducción 4
2
ORDER BY 40
Ejercicios 43
Ejercicio 1 - Viajeros 44
Ejercicio 2 - Hospitales [8] 51
Ejercicio 3 - Empresa distribuidora de alimentos [8] 55
Ejercicio 4 - Tienda de informática [9] 62
Ejercicio 5 - Empleados [9] 67
Ejercicio 6 - Los almacenes [9] 71
Ejercicio 7 - Películas y salas [9] 74
Ejercicio 8 - Los Directores [9] 76
Ejercicio 9 - Corretaje de Propiedades [10] 79
Ejercicio 10 - Piezas y Proveedores [9] 81
Ejercicio 11 - Departamentos y Empleados [10] 83
Ejercicio 12 - Control de Stock y facturación [11] 87
Ejercicio 13 - Pedidos [12] 91
Ejercicio 14 - Locales Nocturnos 94
Ejercicio 15 - Empleados de una empresa 97
Ejercicio 16 - Departamentos y empleados [13] 100
Ejercicio 17 - Empleados de una empresa [14] 102
Ejercicio 18 - Libros [15] 109
Ejercicio 19 - Juegos de la NBA 112
Ejercicio 20 - Proveedores y componentes [16] 117
Ejercicio 21 -Venta de Productos [18] 125
Ejercicio 22 - Oficina ferretera [17] 128
Ejercicio 23 - Empresa [19] 142
Ejercicio 24 - Parque Temático [20] 148
Ejercicio 25 - Vuelta Ciclista [21] 162
Ejercicio 26 - Proyectos de Construcción 172
Ejercicio 27 - Empresas de envíos [21] 178
Ejercicio 28 - Titulaciones 186
3
Introducción
Esta guía tiene como objetivo fundamental convertirse en un texto de apoyo para los estudiantes
de la asignatura Sistemas de Bases de Datos I impartida en la Escuela de Ingeniería
Informática de la Facultad de Ingeniería de la Universidad Católica Andrés Bello.
Con la guía el estudiante tendrá un resumen de los conceptos básicos sobre bases de datos
relacionales y un compendio de ejercicios resueltos utilizando el Lenguaje de Consulta
Estructurado o conocido por su definición en inglés Structured Query Language (SQL), en ésta
se presentan casos prácticos, sin embargo, éste trabajo no pretende sustituir textos
académicos, por el contrario pretende apoyar al estudiante en el proceso de aprendizaje del
lenguaje utilizado para interactuar con sistemas manejadores de bases de datos.
Los ejercicios propuestos se presentan con la solución para que el estudiante pueda analizar y
comparar dicha solución con la suya. El contenido de la guía se agrupa en cinco capítulos, a
continuación se presenta una breve descripción de cada uno de los capítulos:
4
Capítulo
Bases de Datơs Rela›io>ales
“Una base de datơ‹ típi›a rep›ese 9a algún aspe›to del mu tơ real y es utilisada po2 unơ o más
g2upơs de us a2iơ‹ co fines espe›íficos” [1]
5
El término base de datos ha sido utilizado para referirse a cualquier cosa, desde una
colección de nombres y direcciones, hasta un complejo sistema de recuperación y
almacenamiento de datos que se basa en interfaces de usuarios, una red de
computadoras y servidores. Hay tantas definiciones para base de datos como libros
sobre éstas. Por otra parte, los distintos proveedores de DBMS (Data Base Management
System) han desarrollado diferentes arquitecturas, por lo que no todas las bases de
datos están diseñadas de la misma manera. A pesar de la falta de una definición
absoluta, la mayoría de las fuentes coinciden en que una base de datos, por lo menos,
es una colección de datos organizada en un formato estructurado que es definido
como metadatos que describe esa estructura. Puede pensar en los metadatos como
información sobre los datos almacenados, que define cómo se almacenan éstos en una
base de datos [2].
Por tanto una base de datos se puede definir como una colección de datos
relacionados. La palabra datos se refiere a los hechos conocidos que se pueden grabar
y que tienen un significado implícito, también representa algún aspecto del mundo
real, lo que en ocasiones se denomina minimundo o universo de discurso.
6
Modelo Relacional
Fue introducido en el año
1970 por E. F. Codd y define
una estructura de datos
relacional que protege los
datos y permite que sean
manipulados de manera que
es previsible y resistente al
error. El modelo relacional, el
cual se basa principalmente
en los principios matemáticos
de la teoría de conjuntos y
lógica de predicados, apoya la recuperación de datos sencilla, aplica la integración de
datos (la precisión y coherencia de los datos), y proporciona una estructura de base
de datos independiente de las aplicaciones al acceder a los datos almacenados. El
núcleo del modelo relacional es la relación. [3]
Entidad
Una entidad es una «cosa» u «objeto» en el mundo real que es distinguible de todos
los demás objetos. Una entidad tiene un conjunto de propiedades, y los valores para algún
conjunto de propiedades pueden identificar una entidad de forma unívoca. Por ejemplo,
7
la C.I. 6.789.901 identifica unívocamente una persona particular. Análogamente, se puede
pensar en los préstamos bancarios como entidades, y un número de préstamo P-15 en
la sucursal de la Castellana identifica unívocamente una entidad de préstamo. Una entidad
puede ser concreta, como una persona o un libro, o puede ser abstracta, como un
préstamo, unas vacaciones o un concepto [4].
Atributos
Un atributo, como se usa en el modelo E-R, se puede caracterizar por los siguientes tipos
de atributo:
8
El valor de un atributo compuesto es la concatenación de los valores de sus
atributos simples. [1]
➔ Atributos monovalor y multivalor. La mayoría de los atributos tienen un solo valor
para una entidad en particular; dichos atributos reciben el nombre de monovalor o
de un solo valor. Por ejemplo, Edad es un atributo monovalor de una persona.
En algunos casos, un atributo puede tener un conjunto de valores para la
misma entidad (por ejemplo, un atributo Colores para un vehículo, o un
atributo Licenciaturas para una persona). Los vehículos con un solo color tiene
un solo valor, mientras que los vehículos de dos tonos tienen dos valores de
color. De forma parecida, puede que una persona no tenga ninguna
licenciatura, otra puede que tenga una, y una tercera persona puede que tenga
dos o más; por consiguiente, diferentes personas pueden tener una cantidad de
valores diferente para el atributo Licenciaturas. Dichos atributos se denominan
multivalor. Un atributo multivalor puede tener límites superior e inferior para
restringir el número de valores permitidos para cada entidad individual.[1]
➔ Atributos almacenados y derivados. En algunos casos, dos (o más) valores de
atributo están relacionados (por ejemplo, los atributos Edad y FechaNac de una
persona). Para una entidad de persona en particular, el valor de Edad puede
determinarse a partir de la fecha actual (el día de hoy) y el valor de FechaNac de
esa persona. El atributo Edad se denomina entonces atributo derivado y se dice
que se ha derivado del atributo FechaNac, que es el denominado atributo
almacenado. Algunos valores de atributo se pueden derivar de entidades
relacionadas; por ejemplo, un atributo NumEmpleados de una entidad
DEPARTAMENTO puede derivarse contando el número de empleados
relacionados con (o que trabajan para) ese departamento. [1]
Relación
Una relación es una asociación entre diferentes entidades. Por ejemplo, se puede definir
una relación que asocie al cliente López con el préstamo P-15. Esta relación
específica
9
que López es un cliente con el préstamo número P-15. Un conjunto de relaciones es
un conjunto de relaciones del mismo tipo. [4]
Es una colección de programas que permite a los usuarios crear y mantener una base
de datos. El DBMS es un sistema de software de propósito general que facilita los
procesos de definición, construcción, manipulación y compartición de bases de datos
entre varios usuarios y aplicaciones. Definir una base de datos implica especificar los tipos
de datos, estructuras y restricciones de los datos que se almacenarán en la base de
datos. La definición o información descriptiva de una base de datos también se
almacena en esta última en forma de catálogo o diccionario de la base de datos; es lo
que se conoce como metadatos. La construcción de la base de datos es el proceso
consistente en almacenar los datos en algún medio de almacenamiento controlado por
el DBMS. La manipulación de una base de datos incluye funciones como la consulta de
la base de datos para recuperar datos específicos, actualizar la base de datos para
reflejar los cambios introducidos en el minimundo y generar informes a partir de los
datos. Compartir una base de datos permite que varios usuarios y programas accedan
a la base de datos de forma simultánea. Una aplicación accede a la base de datos
enviando consultas o solicitudes de datos al DBMS. Una consulta normalmente
provoca la recuperación de
10
algunos datos; una transacción puede provocar la lectura o la escritura de algunos
datos en la base de datos.
11
Capítulo
SQ£: Leng aje de Cons Jta Est›uct ›ado
“El le p aje SQ£ se puebe co ‹ide2a› co ơ una de las p2i>cipaJes ra›ơ>es del éxitơ co e›cial de las
base‹ de datơ‹ rela›ionale‹.” [1]
12
El lenguaje SQL se puede considerar como una de las principales razones del éxito
comercial de las bases de datos relacionales. Como se convirtió en un estándar para
estas últimas, los usuarios perdieron el miedo a migrar sus aplicaciones de base de
datos desde otros tipos de sistemas de bases de datos (por ejemplo, sistemas de red o
jerárquicos) a los sistemas relacionales, porque aunque estuvieran satisfechos con el
producto DBMS relacional que estaban utilizando, no esperaban que la conversión a
otro producto DBMS relacional fuera caro y consumiera mucho tiempo, ya que ambos
sistemas seguían los mismos estándares en cuanto al lenguaje. En la práctica, por
supuesto, hay muchas diferencias entre los distintos paquetes DBMS relacionales
comerciales. Sin embargo, si el usuario sólo utiliza las funciones que forman parte del
estándar, y si ambos sistemas relacionales soportan fielmente el estándar, la
conversión entre los dos sistemas es mucho más sencilla. Otra ventaja de disponer de
un estándar es que los usuarios pueden escribir sentencias en una aplicación de base
de datos para acceder a los datos almacenados en dos o más DBMSs relacionales sin
tener que cambiar el sublenguaje de base de datos (SQL), siempre y cuando esos
DBMS soporten el SQL estándar. [1]
Historia de SQL
La historia de SQL empieza en 1974 con la definición, por parte de Donald Chamberlin
y de otras personas que trabajaban en los laboratorios de investigación de IBM, de un
lenguaje para la especificación de las características de las bases de datos que adopta
el modelo relacional. Este lenguaje se llamaba SEQUEL (Structured English Query
Language) y se implementó en un prototipo llamado SEQUEL-XRM entre 1974 y 1975.
Las experimentaciones con ese prototipo condujeron, entre 1976 y 1977, a una
revisión del lenguaje (SEQUEL/2), que a partir de ese momento cambió de
nombre por motivos legales, convirtiéndose en SQL [5].
El prototipo (System R), basado en este lenguaje, se adoptó y utilizó internamente en IBM
y lo adoptaron algunos de sus clientes elegidos. Gracias al éxito de este sistema, que
no
13
estaba todavía comercializado, también otras compañías empezaron a desarrollar sus
productos relacionales basados en SQL. A partir de 1981, IBM comenzó a entregar sus
productos relacionales y en 1983 empezó a vender DB2. En el curso de los años
ochenta, numerosas compañías (por ejemplo Oracle y Sybase, sólo por mencionar
algunos) comercializaron productos basados en SQL, que se convierte en el estándar
industrial que respecta a las bases de datos relacionales. En 1986, el ANSI (American
National Standards Institute) adoptó SQL como estándar para los lenguajes
relacionales y en 1987 se transformó en estándar ISO (International Standards
Organization) [1].
En los años siguientes, SQL ha sufrido diversas revisiones que han conducido primero a
la versión SQL/89, posteriormente la versión SQL/92, y la SQL/1999, y la actual
SQL/2016. El hecho de tener un estándar definido por un lenguaje para bases de datos
relacionales abre potencialmente el camino a la intercomunicabilidad entre todos los
productos que se basan en él. En general cada productor adopta e implementa en la
propia base de datos sólo el corazón del lenguaje SQL, extendiéndose de manera
individual según la propia visión que cada cual tenga del mundo de las bases de datos.
SQL
El nombre SQL significa Lenguaje de Consulta Estructurado (Structured Query
Language). Es un lenguaje de bases de datos global, cuenta con sentencias para
definir datos, consultas y actualizaciones. Además, dispone de características para definir
vistas en la base de datos, especificar temas de seguridad, autorización, definir
restricciones de integridad y especificar controles de transacciones. También tiene
reglas para incrustar sentencias de SQL en un lenguaje de programación de propósito
general, como Java, C/C++, entre otros.
14
base
15
de datos, asegurar esos objetos y manipular la información dentro de los objetos. Un
método común usado para categorizar las instrucciones SQL es dividirlas de acuerdo
con las funciones que realizan. Basado en este método, SQL se separa en tres tipos de
instrucciones:
16
SELECT para recuperar datos de una tabla y la instrucción INSERT para
agregar datos a una tabla.
17
Una sentencia SQL es como una frase que dice lo que se quiere obtener y de donde
obtenerlo. Todas las sentencias empiezan con un verbo (palabra reservada que indica
la acción a realizar), seguido del resto de cláusulas, algunas obligatorias y otras opcionales
que completan la frase. Todas las sentencias siguen una sintaxis para que se puedan
ejecutar correctamente, dichas sentencias SQL pueden variar entre los diferentes
motores.
18
Capítulo
Leng aje de Defini›ión de Datơs (DD£)
“SQ£ in›J ye co a>dos pa2a c2ea› obje9os de base de datơ‹ co ơ tabJas, ínbi›es, vis9as, ent›e
ot2ơ‹.” [7]
19
Creación de una Base de Datos
A pesar del hecho de que el estándar SQL no
define qué es una base de datos, y mucho menos
proporciona una instrucción para crear cualquier
tipo de base de datos objeto, la mayoría de los
RDBMS respaldan la creación de una base de
datos objeto, además puedan utilizar a ese objeto
como base para su estructura jerárquica en la gestión de datos objetos.
Sintaxis:
Ejemplo:
➔ Tipos de datos numéricos: Los valores especificados por los tipos de datos
numéricos son números. Todos los tipos de datos numéricos tienen una precisión,
y algunos tienen una escala. La precisión se refiere al número de dígitos
(dentro de un valor numérico específico) que se pueden almacenar. La escala se
refiere al número de dígitos en la parte fraccional de ese valor (los dígitos a la
derecha del punto decimal). Por ejemplo, el número 435.27 tiene una precisión
de 5 y una escala de 2. La escala no puede ser un número negativo o ser más
larga que la precisión. Una escala de 0 indica que el número es un número
entero y no contiene ningún componente fraccional. SQL define dos formas de
tipos de datos numéricos:
◆ Numéricos exactos: Tienen precisión y escala. Los tipos de datos
numéricos exactos incluyen:
2
● NUMERIC
● DECIMAL
● INTEGER
● SMALLINT
2
Especificación de restricciones y valores predeterminados
de atributo
SQL permite NULL como valor de atributo, es posible especificar una restricción NOT
NULL si no se permite NULL para un atributo en particular. Esto siempre se especifica
implícitamente para los atributos que forman parte de la clave principal de cada relación,
pero puede especificarse para cualquier otro atributo para cuyo valor se exige que no
sea NULL. También es posible definir un valor predeterminado para un atributo
añadiendo la cláusula DEFAULT <valor> a su definición. El valor predeterminado se
incluye en cualquier tupla nueva si no se proporciona un valor explícito para ese atributo.
Si no se especifica una cláusula predeterminada, el valor predeterminado es NULL
para los atributos que no tienen la restricción NOT NULL.
Ejemplo:
23
Otro tipo de restricción puede ser restringir los valores de atributo o dominio con la
cláusula CHECK. Por ejemplo, suponga que los números de departamento están
restringidos a número enteros entre 1 y 20.
Ejemplo:
NumeroDpto NUMBER NOT NULL CHECK (NumeroDpto > O AND NumeroDpto < 21);
Creación de tablas
SQL respalda tres tipos de tablas: tablas base, tablas derivadas y tablas vistas. La
mayoría de las tablas base son objetos de esquema que tienen los datos de SQL. Las
tablas derivadas son los resultados que se observan cuando se solicitan (consultan)
datos de una base de datos. Las tablas vistas son otro nombre para las vista.
Se puede utilizar una forma de la instrucción CREATE TABLE para crear todos los tipos
de tablas, excepto las tablas temporales locales declaradas. [2]
Ejemplo:
Modificación de tablas
25
| ALTER [COLUMN] <nombre de columna> { SET DEFAULT <valor
predeterminado> | DROP DEFAULT }
Ejemplo:
Eliminación de tablas
La única decisión que necesita tomar cuando se elimina una tabla es si debe escoger
la opción CASCADE o RESTRICT. Si se utiliza CASCADE, la tabla y sus datos se eliminan,
junto con todas las vistas, restricciones, rutas o activadores que hacen referencia a la
tabla. Si se utiliza RESTRICT, la tabla se elimina sólo si no existen dependencias. [2]
Ejemplo:
26
Restricción de Integridad
Una base de datos SQL debe hacer más que sólo almacenar datos. Se debe asegurar
que el almacenamiento de los datos es el correcto. Si la integridad de los datos se
compromete, los datos pueden ser inexactos o inconsistentes, poniendo en
cuestionamiento la fiabilidad de la base de datos. Con el fin de asegurar la integridad de
los datos, SQL proporciona una serie de restricciones de integridad, reglas que se
aplican a la base de datos para restringir los valores que se pueden colocar en esas
tablas. Se pueden aplicar restricciones a columnas individuales, a tablas individuales o a
múltiples tablas.
Ejemplo:
27
➔ Restricción UNIQUE: La restricción UNIQUE permite exigir que una columna o
conjunto de columnas contengan valores únicos, valores significativos que sean
diferentes de todas las demás filas en la misma tabla. Para crear una
restricción de columna, se debe añadir como parte de la definición de una
columna, como se muestra en la siguiente sintaxis:
Ejemplo:
Si se quiere añadir una restricción única como una restricción de tabla, se debe
agregar como un elemento de definición de tabla, como se muestra en la
siguiente sintaxis:
Ejemplo:
28
la que se conoce como una restricción referencial (en relación con otra tabla). Las
tablas en una base de datos relacional están unidas entre sí de una manera
significativa con el fin de garantizar la integridad de los datos. Esta asociación
entre tablas forma una relación que proporciona una integridad referencial entre
las tablas. La integridad referencial evita la manipulación de los datos en una tabla
que afecte negativamente los datos en otra tabla. [2]
Si se quiere añadir una restricción foreign key como una restricción de tabla, se
debe agregar como un elemento de definición de tabla, como se muestra en la
siguiente sintaxis:
Ejemplo:
CREATE TABLE TITULOS_CD
( ID_TITULO_CD INT,
TITULO_CD VARCHAR(60),
ID_EDITOR INT,
CONSTRAINT FK_ID_EDITOR FOREIGN KEY (ID_EDITOR)
REFERENCES EDITORES_CD (ID_EDITOR) );
Ejemplo:
CREATE TABLE TITULOS_CD
( ID_TITULO_CD INT,
TITULO_CD VARCHAR(60),
ID_EDITOR INT REFERENCES EDITORES_CD );
29
➔ Restricción CHECK: Se puede definir como restricciones de tabla, restricciones
de columna, restricciones de dominio, o en afirmaciones. Una restricción
CHECK permite especificar qué valores se pueden incluir en una columna. Se
puede definir un rango de valores (por ejemplo, entre 10 y 100), una lista de
valores (por ejemplo, blues, jazz, pop, country), o una serie de otras
condiciones que restringen exactamente qué valores se permiten en una
columna. La sintaxis básica para una restricción CHECK es relativamente
sencilla. Para crear una restricción CHECK de columna, utilice la siguiente
sintaxis en la definición de columna:
<nombre de columna> { <tipo de datos> | <dominio> }
CHECK ( <condición de búsqueda> )
Para crear una restricción CHECK de tabla, utilice la siguiente sintaxis en la definición de
la tabla:
[ CONSTRAINT <nombre de restricción> ]
CHECK ( <condición de búsqueda> )
Ejemplos:
CREATE TABLE TITULOS_CD
( ID_DISCO_COMPACTO INT,
TITULO_CD VARCHAR(60) NOT NULL,
ERA CHAR(5),
CONSTRAINT CK_ERA CHECK ( ERA IN ( '1940s', '1950s','1960s',
'1970s', '1980s', '1990s', '2000s' ) ) );
30
Vistas en SQL
Una vista en terminología SQL es una tabla que deriva de otras tablas. Esas otras
tablas pueden ser tablas base o vistas definidas anteriormente. Una vista no existe
necesariamente en formato físico; está considerada como una tabla virtual, en oposición
a las tablas base, cuyas tuplas están realmente almacenadas en la base de datos. Esto
limita las posibles operaciones de actualización que pueden aplicarse a las vistas,
pero no ofrecen limitación alguna al consultar una vista. Una vista es una forma de
especificar una tabla a la que nos referimos con frecuencia, aunque no exista físicamente.
En SQL se utiliza el comando CREATE VIEW para especificar una vista. A una vista se le
asigna un nombre de tabla (virtual), o nombre de vista, una lista de nombres de
atributos y una consulta que sirve para especificar el contenido de la vista. Si ninguno
de los atributos de la vista resulta de aplicar funciones u operaciones aritméticas, no
es necesario especificar nombres de atributos para la vista, puesto que serían
idénticos a los de los atributos de las tablas de definición.
Ejemplo:
CREATE VIEW TRABAJA AS
SELECT Nombre, Apellido1, NombreProyecto, Horas
FROM EMPLEADO,PROYECTO,TRABAJA_EN
WHERE Dni = DniEmpleado AND NumProy = NumProyecto;
Se supone que una vista siempre está actualizada; si se modifican las tuplas de las
tablas base sobre las que se define la vista, esta última debe reflejar esos cambios
automáticamente. Por tanto, la vista no se materializa al definir la vista, sino al
especificar una consulta en la vista. La tarea de que la vista esté actualizada es
responsabilidad del DBMS, y no del usuario. Si ya no se necesita una vista, se puede
utilizar el comando DROP VIEW para eliminarla.
Ejemplo:
31
Capítulo
Leng aje de ManipvJación de Datơs (DN£)
“Una de las fu ›iones p2i>cipaJes de cualqvier base de datơ‹ es la capa›idab de ma ejar los datơ‹
al a›enabơ‹ de 9rơ de sus tabJas.” [2]
32
Insertar datos en SQL
La instrucción INSERT permite agregar datos a las diferentes tablas en una base de
datos. La sintaxis de una instrucción INSERT básica es relativamente sencilla:
Sintaxis:
INSERT INTO <nombre de la tabla>
[ ( <nombre de la columna> ) [ { ,<nombre de la columna> }... ] ) ]
VALUES ( <valor> [ { , <valor> }... ] )
Ejemplo:
INSERT INTO facultad (fac_codigo, fac_nombre)
VALUES ( 1 , 'Humanidades')
33
3. Se debe proporcionar un valor por cada columna en la tabla excepto para las
columnas que permiten valores nulos o que tienen un valor definido por defecto.
4. Cada valor con un carácter del tipo de datos de cadena debe estar encerrado
en comillas simples.
5. Se puede utilizar la palabra clave NULL (o null) como el valor de los datos en la
cláusula VALUES para asignar un valor nulo a cualquier columna que permita
valores nulos.
Sintaxis:
UPDATE <nombre de la tabla>
SET <determinar expresión de la cláusula> [{,<determinar expresión de la
cláusula> }... ] [
WHERE <condición de búsqueda> ]
Ejemplo:
UPDATE estudiante
SET inscrito = 'SI'
Como se puede ver, la cláusula UPDATE y la cláusula SET son obligatorias, mientras
que la cláusula WHERE es opcional. En la cláusula UPDATE se debe especificar el
nombre de la tabla que se está actualizando. En la cláusula SET se debe especificar
una o más expresiones de cláusula, es decir, se especifica los atributos que se
modificarán y sus nuevos valores. En la cláusula WHERE, se debe especificar una
condición de búsqueda, se especifica una condición o conjunto de condiciones que
actúa como un filtro para las filas que se están actualizando. Solamente las filas que
cumplen con estas condiciones son actualizadas.
34
Insertar valores desde una instrucción SELECT
Para insertar datos se considera la cláusula VALUES como obligatoria, sin embargo,
existe una alternativa y es que se puede utilizar una instrucción SELECT para especificar
los valores que se quieran ingresar en una tabla. La clave para utilizar una instrucción
SELECT, al igual que al utilizar una cláusula VALUES, es asegurarse que el número de
valores aplicados por la instrucción SELECT coincida con el número requerido de
valores en la tabla, y que éstos cumplan con cualquier restricción de la tabla
correspondiente.
Ejemplo:
INSERT INTO INVENTARIO_CD_2
SELECT NOMBRE_CD, EN_EXISTENCIA FROM INVENTARIO_CD;
Ejemplo:
UPDATE INVENTARIO_CD_2
SET EN_EXISTENCIA_2 = ( SELECT AVG(EN_EXISTENCIA) FROM INVENTARIO_CD );
Ejemplo:
DELETE FROM EMPLEADO
WHERE Apellido = 'Cabrera';
La instrucción SELECT es una expresión de consulta que comienza con la palabra clave
SELECT e incluye una serie de elementos que forman la expresión. La sintaxis básica
para la instrucción SELECT puede dividirse en varias cláusulas específicas, cada una de
las cuales ayuda a refinar la consulta para que sólo se devuelvan los datos requeridos.
La sintaxis para la instrucción SELECT puede mostrarse como sigue:
Donde:
36
Las cláusulas FROM, WHERE, GROUP BY y HAVING hacen referencia como expresiones
de tabla. Esta porción de la instrucción SELECT siempre se evalúa en el orden
indicado en la sintaxis. El resultado de esa evaluación es una tabla virtual que se
utiliza en la evaluación posterior.
Ejemplo:
SELECT Nombre, EMPLEADO. Nombre, Dirección
FROM EMPLEADO, DEPARTAMENTO
WHERE DEPARTAMENTO.Nombre='Investígación'
AND DEPARTAMENTO.NumeroDpto = EMPLEADO.NumeroDpto;
La ambigüedad también aparece en el caso de las consultas que se refieren dos veces
a la misma relación, como en el siguiente ejemplo:
37
Ejemplo:
SELECT E.Nombre, E.Apellido, S.Nombre, S.Apellido
FROM EMPLEADO AS E, EMPLEADO AS S
WHERE E.SuperDni = S.Dni;
LIKE
El LlKE se puede utilizar para la comparación de patrones. Las cadenas parciales se
especifican mediante dos caracteres reservados [1]:
Predicado IN
El predicado IN permite determinar si los valores en la columna especificada de una
tabla están contenidos en una lista definida o contenidos dentro de otra tabla. En el
primer caso, se debe especificar el nombre de la columna, la palabra clave IN y una lista
de valores que son comparados a los valores en la columna especificada. En el
segundo caso, se debe especificar el nombre de la columna, la palabra clave IN y una
subconsulta, que hace referencia a la segunda tabla. En cada caso, si el valor de la
columna coincide con uno de los valores en la lista o en los resultados de la
subconsulta, el predicado se evalúa como verdadero y la fila es arrojada en los
resultados de la consulta.
38
Ejemplos:
SELECT NOMBRE_CD, EN_EXISTENCIA FROM INVENTARIO_DISCO_COMPACTO
WHERE EN_EXISTENCIA IN ( 12, 22, 32, 42 );
Predicado NULL
El predicado NULL resulta muy simple de implementar. Utilizado en conjunción con la
palabra clave IS, el predicado se agrega a una cláusula WHERE de la misma forma que
cualquier otro predicado, y se aplica sólo a los valores nulos que pudieran existir en la
columna que se está consultando.
Ejemplo:
SELECT *
FROM BIO_ARTISTAS
WHERE LUGAR_DE_NACIMIENTO IS NULL;
Predicado BETWEEN
El predicado BETWEEN se utiliza en conjunción con la palabra clave AND para
identificar un rango de valores que pueden ser incluidos como una condición de
búsqueda en la cláusula WHERE. Los valores en la columna identificada deben entrar
en ese rango para poder evaluarse como verdaderos. Cuando se utiliza la cláusula
BETWEEN, se debe especificar la columna aplicable, el valor más bajo del rango y el
valor más alto del rango.
Ejemplo:
39
Resumen de Operadores
GROUP BY
La cláusula GROUP BY tiene una función muy diferente de la cláusula WHERE. Como
su nombre lo indica, la cláusula GROUP BY se utiliza para agrupar tipos de información
con el fin de resumir datos relacionados. La cláusula GROUP BY se puede incluir en la
instrucción SELECT aun si la cláusula WHERE se utiliza o no. Esta cláusula especifica
los atributos de agrupamiento, que también deben aparecer en la cláusula SELECT,
por lo
40
que el valor resultante de aplicar la función de agregación a un grupo de tuplas
aparece junto con el valor de los atributos de agrupamiento [1].
Ejemplo:
SELECT NumProyecto, NombreProyecto, COUNT(*)
FROM PROYECTO, TRABAJA_EN
WHERE NumProyecto = NumProy
GROUP BY NumProyecto, NombreProyecto;
Ejemplo:
SELECT PRECIO, CATEGORIA, SUM(A_LA_MANO) AS TOTAL_ A_LA_MANO
FROM EXISTENCIA_DISCO_COMPACTO
GROUP BY PRECIO, CATEGORIA
HAVING SUM(A_LA_MANO) > 10;
ORDER BY
La cláusula ORDER BY, cuando se usa en la instrucción SELECT, es la última cláusula
procesada. La cláusula ORDER BY toma la salida de la cláusula SELECT y ordena los
resultados de la consulta de acuerdo con las especificaciones dentro de la cláusula
ORDER BY. La cláusula no agrupa las filas, como se agrupan por la cláusula GROUP BY,
ni filtra las filas, como se filtran por la cláusula WHERE o la cláusula HAVING. Sin
embargo, se puede especificar si las filas se organizan en un orden ascendente
(utilizando la palabra clave ASC) o en orden descendente (usando la palabra clave
DESC).
Para utilizar la cláusula ORDER BY, simplemente se especifica una o más columnas y
las palabras clave opcionales ASC o DESC (una por columna). Si no se especifica la
palabra
41
clave, se toma ASC. Las filas se organizan de acuerdo con la columna que especifique.
Si se define más de una columna en la cláusula ORDER BY, las filas se organizan en el
orden en que las columnas se especifican.
Ejemplo:
SELECT *
FROM EXISTENCIA_DISCO_COMPACTO
WHERE PRECIO < 16.00
ORDER BY PRECIO, A_LA_MANO DESC
42
Resumen de la sintaxis SQL [1]
43
Capítulo
Eje2›icios
“Una de las fu ›iones p2i>cipaJes de cualqvier base de datơ‹ es la capa›idab de ma ejar los datơ‹
al a›enabơ‹ de 9rơ de sus tabJas.” [2]
44
Ejercicio 1 - Viajeros
Dado el siguiente modelo relacional de una base de datos de una agencia de viajes
Nota: Las claves foráneas en los modelos relacionales presentes en este documento se representan en
cursiva y negrita.
SELECT *
FROM lugar;
45
FROM lugar;
SELECT l_nombre
FROM lugar
WHERE L_clima = 'TROPICAL';
11. Listar todos los países con un total de habitantes que supere los 10 millones.
46
SELECT p_nombre, p_fecha_nacimiento AS Nacido_el
FROM pasajero
WHERE p_perfil IN ('BUSINESS','PRIMERA_CLASE');
15. Listado de todos los pasajeros cuyo nombre empiece por la letra M.
16. Listado de todos los lugares cuyo nombre tenga una letra A.
SELECT l_nombre
FROM lugar
WHERE l_nombre LIKE '%A%';
17. Listar los diferentes apellidos de los pasajeros que empiecen por la letra M y terminen en
EZ.
SELECT l_nombre
FROM lugar
WHERE l_clima IS NOT NULL;
20. Listado de todos los pasajeros que contengan la letra “Y” en su nombre y que
hayan nacido entre el año 1975 y el 1985.
47
SELECT p_nombre, p_apellido
FROM pasajero
WHERE p_nombre LIKE '%Y%'
AND p_fecha_nacimiento BETWEEN '01-01-1975' AND '31-12-1985';
21. Listado viajeros que tienen el perfil LOW_COST y tengan apellido Ruiz.
22. Listado de los lugares que no tengan informado el número total de habitantes, su nombre
empiece por C, con clima desconocido o Mediterráneo.
23. Listado con los lugares de clima desconocido y que tengan la palabra ciudad en
su nombre o que el total de sus habitantes sea inferior a 5 millones.
24. Listar los pasajeros nacidos después de 1970 que viajen con el perfil business class
y que tenga una G en su nombre.
25. Mostrar los países que no tengan entre 50 y 100 millones de habitantes y estén
en Europa o Asia y además tengan una M en su nombre.
48
FROM lugar p, lugar c
WHERE p.l_total_habitantes NOT BETWEEN 50000000 AND
100000000 AND p.l_tipo = 'PAIS'
AND p.l_nombre LIKE '%M%'
AND p.l_fk_lugar = c.l_codigo
AND c.l_tipo = 'CONTINENTE'
AND c.l_nombre IN ('EUROPA','ASIA');
27. Listar los pasajeros por orden alfabético de su apellido, mostrarlos de la forma Apellido,
Nombre y etiquetar la columna como Nombre y Apellido.
29. Mostrar los países de Europa ordenándolos por su número de habitantes de menor
a mayor.
30. Mostrar los viajeros ordenados por su fecha de nacimiento (de más joven a menos) y
por su apellido de forma inversa.
49
31. Mostrar los diferentes continentes ordenados alfabéticamente.
32. Seleccionar todos aquellos pasajeros que no usen clase business ordenados por su
número de teléfono y apellido.
33. Hacer un listado con los países que no pertenezcan a Europa u Oceanía
ordenados alfabéticamente por su continente y su total de habitantes de mayor a
menor.
50
35. Listar todos los lugares con más de 10000 habitantes, de clima conocido y con las
palabras "UBICADA" y "SUR" ordenados por su nombre y su número de habitantes,
de menor a mayor.
51
Ejercicio 2 - Hospitales [8]
Dado el DDL de la base de datos de hospitales:
Se pide:
1. Listado de todos los miembros del personal cuyo nombre empiece por la letra 'A'.
SELECT apellido
FROM plantilla WHERE apellido LIKE 'A%';
52
2. ¿Quienes son las enfermeras y enfermeros que trabajan en turnos de Tarde o Mañana?
SELECT apellido
FROM plantilla
WHERE funcion IN ('ENFERMERO','ENFERMERA')
AND turno IN ('T','M');
4. Mostrar, para todos los hospitales, el código de hospital, el nombre completo del hospital
y su nombre . Ordenar la recuperación por el nombre.
5. Se desea conocer el máximo salario que existe en cada sala de cada hospital.
53
7. Insertar en la tabla Plantilla al enfermero Garcia J. con un sueldo de 3.000.000 Bs, y
número de empleado 1234. Trabaja en el hospital 22, sala 2, turno matutino.
Solución 1:
INSERT INTO plantilla(hospital_cod, sala_cod, empleado_no, apellido,
funcion, turno, salario)
VALUES (22,2,1234,'Garcia J.','ENFERMERO', 'M',3000000);
Solución 2:
INSERT INTO plantilla
VALUES (22,2,1234,'Garcia J.','ENFERMERO','M',3000000);
UPDATE enfermo
SET direccion = 'MADRID 411'
WHERE inscripcion = 74835;
UPDATE enfermo
SET direccion = NULL;
UPDATE enfermo
SET direccion = (SELECT direccion
FROM enfermo
WHERE inscripcion = 14024)
WHERE inscripcion = 10995;
11. En todos los hospitales del país se ha recibido un aumento del presupuesto, por lo que
se incrementará el número de camas disponibles en un 10%.
UPDATE hospitales
SET num_cama = num_cama + (num_cama * 0.1);
54
12. Defina una vista porque se va a realizar un programa de consulta de la información
sobre enfermos. Los datos a mostrar serán sus apellidos, dirección, fecha de
nacimiento y hospital en el que se encuentran.
55
Ejercicio 3 - Empresa distribuidora de alimentos [8]
Dado el DDL de la base de datos de la empresa. Se pide:
2. Para cada empleado cuyo apellido contenga una "N", se quiere el oficio y apellido. La
salida debe estar ordenada por apellido ascendentemente.
3. Listado de empleados con su salario total (salario más comisión). La salida debe estar
ordenada por el salario y el apellido descendentemente.
SELECT apellido,
(salario + comision) AS salario_total
FROM emp
ORDER BY 2 DESC, 1;
4. Para cada empleado que no tenga comisión o cuya comisión sea mayor que el 15% de
su salario, se pide el salario total que tiene. Este será: salario más su comisión más el
15%
56
del salario. La salida deberá estar ordenada por el oficio y por el salario que le
queda descendentemente.
ORDER BY oficio, 3
DESC ;
13. Listado con el personal de alta, que indique el apellido, oficio y fecha de alta del personal
del departamento número 20 que ganan más de 150.000 Bs Mensuales.
14. Se pide el apellido, oficio y la fecha en que han sido dados de alta los empleados
de la empresa, pero solo de aquellos cuyo fecha de alta sea posterior al año 2018.
Ordenado por oficio.
16. Encontrar el salario más alto y el salario más bajo de la tabla de empleados, así como la
diferencia entre ambos.
57
17. Calcular el número de oficios diferentes que hay en total, en los departamentos 10 y 20
de la empresa.
18. Calcular el número de personas que realizan cada oficio en cada departamento.
19. Se desea saber el salario medio total (salario más comisión) anual de los vendedores
de nuestra empresa.
20. Se desea saber el salario medio total (salario más comisión) anual, tanto de los
empleados como de los vendedores de nuestra empresa.
21. Se desea saber para cada departamento y en cada oficio, el máximo salario y la suma
total de salarios, pero solo de aquellos departamentos y oficios cuya suma salarial supere
o sea igual que el 50% de su máximo salario. En el muestreo, solo se debe estudiar a
aquellos empleados que no tienen comisión o la tengan menor que el 25% de su
salario.
58
22. Listar el apellido de cada empleado, su oficio, su número de departamento y el
nombre del departamento donde trabajan.
24. Sedesea conocer el nombre y oficio de todos aquellos empleados que trabajan en
Madrid. La salida deberá estar ordenada por el oficio.
25. Se desea conocer cuántos empleados existen en cada departamento. Devolviendo una
salida ordenada por el número de empleados descendentemente.
59
26. Se desea conocer, tanto para el departamento de VENTAS, como para el de
CONTABILIDAD, su máximo, su mínimo y su media salarial, así como el número de
empleados en cada departamento. La salida deberá estar ordenada por el nombre del
departamento.
60
29. Con el uso de subconsultas. Obtener el apellido, departamento y oficio de aquellos
empleados que tengan un oficio, que esté en el departamento 20 y que no sea ninguno
de los oficios que está en el departamento de VENTAS.
31. Queremos conocer el apellido, oficio, salario y departamento en el que trabajan, de todos
los individuos cuyo salario sea mayor que el mayor salario del departamento 30
32. Presentar los nombres y oficios de todos los empleados del departamento 20, cuyo
trabajo sea idéntico al de cualquiera de los empleados del departamento de VENTAS.
61
33. Sedesea obtener todos los empleados de los departamentos que no ganan ni el
máximo ni el mínimo salarial de la empresa.
34. Se desea obtener, para cada departamento, su mínimo y su máximo salarial. Para ello, no
se tendrá en cuenta a los empleados cuyo apellido, coincida con nombre del
departamento en que trabajan. Asimismo, se tendrá en cuenta a aquellos
departamentos cuya diferencia entre el máximo y el mínimo excede la media salarial
de toda la empresa.
62
Ejercicio 4 - Tienda de informática [9]
Dado el siguiente Modelo Entidad Relación, se pide:
SELECT Nombre
FROM ARTICULOS;
3. Obtener el nombre de los productos cuyo precio sea menor o igual a 200 Bs.
SELECT Nombre
FROM ARTICULOS
WHERE Precio > 200;
4. Obtener todos los datos de los artículos cuyo precio esté entre los 60 Bs y los 120 Bs
(ambas cantidades incluidas).
Solución 1:
SELECT * FROM ARTICULOS
WHERE Precio >= 60 AND Precio <= 120;
Solución 2:
SELECT * FROM ARTICULOS
WHERE Precio BETWEEN 60 AND 120;
63
SELECT AVG(Precio)
FROM ARTICULOS;
SELECT AVG(Precio)
FROM ARTICULOS
WHERE Fabricante=2;
8. Obtener el número de artículos cuyo precio sea mayor o igual a 180 Bs.
SELECT COUNT(*)
FROM ARTICULOS
WHERE Precio >= 180;
9. Obtener el nombre y precio de los artículos cuyo precio sea mayor o igual a 180 Bs y
ordenarlos descendentemente por precio, y luego ascendentemente por nombre.
10. Obtener un listado completo de artículos, incluyendo por cada artículo los datos del
artículo y de su fabricante.
64
11. Obtener un listado de artículos, incluyendo el nombre del artículo, su precio, y el nombre
de su fabricante.
12. Obtener el precio medio de los productos de cada fabricante, mostrando solo los
códigos de fabricante.
13. Obtener el precio medio de los productos de cada fabricante, mostrando el nombre
del fabricante.
14. Obtener los nombres de los fabricantes que ofrezcan productos cuyo precio medio sea
mayor o igual a 150 Bs. Indicar el precio medio.
Solución 1 con inner join implicito:
SELECT AVG(Precio), FABRICANTES.Nombre
FROM ARTICULOS, FABRICANTES
WHERE ARTICULOS.Fabricante = FABRICANTES.Codigo
GROUP BY FABRICANTES.Nombre
HAVING AVG(Precio) >= 150;
65
Solución 2 con inner join explicito:
SELECT AVG(Precio), FABRICANTES.Nombre
FROM ARTICULOS INNER JOIN FABRICANTES
ON ARTICULOS.Fabricante = FABRICANTES.Codigo
GROUP BY FABRICANTES.Nombre
HAVING AVG(Precio) >= 150;
16. Obtener una lista con el nombre y precio de los artículos más caros de cada proveedor
(incluyendo el nombre del proveedor).
UPDATE ARTICULOS
SET Nombre = 'Impresora Laser'
WHERE Codigo = 8;
66
19. Aplicar un descuento del 10 % a todos los productos.
UPDATE ARTICULOS
SET Precio = Precio * 0.9;
20. Aplicar un descuento de 10 Bs a todos los productos cuyo precio sea mayor o igual a 120.
UPDATE ARTICULOS
SET Precio = Precio - 10
WHERE Precio >= 120;
67
Ejercicio 5 - Empleados [9]
Dado el siguiente Modelo Entidad Relación, se pide:
SELECT Apellidos
FROM EMPLEADOS;
SELECT *
FROM EMPLEADOS
WHERE Apellidos = 'LOPEZ';
4. Obtener todos los datos de los empleados que se apellidan ’LOPEZ’ y los que se
apellidan ’PEREZ’.
Solución 1 :
SELECT *
FROM EMPLEADOS
WHERE Apellidos = 'LOPEZ' OR Apellidos = 'PEREZ';
Solución 2 :
SELECT *
FROM EMPLEADOS
WHERE Apellidos IN ('LOPEZ' , 'PEREZ');
5. Obtener todos los datos de los empleados que trabajan para el departamento 14.
SELECT *
FROM EMPLEADOS
WHERE Departamento = 14;
68
6. Obtener todos los datos de los empleados que trabajan para el departamento 37 y
para el departamento 77.
Solución 1 :
SELECT *
FROM EMPLEADOS
WHERE Departamento = 37 OR Departamento = 77;
Solución 2:
SELECT *
FROM EMPLEADOS
WHERE Departamento IN (37,77);
7. Obtener todos los datos de los empleados cuyo apellido comience por ’P’.
SELECT *
FROM EMPLEADOS
WHERE Apellidos LIKE 'P%';
SELECT SUM(Presupuesto)
FROM DEPARTAMENTOS;
10. Obtener un listado completo de empleados, incluyendo por cada empleado los dato
del empleado y de su departamento.
SELECT *
FROM EMPLEADOS INNER JOIN DEPARTAMENTOS
ON EMPLEADOS.Departamento = DEPARTAMENTOS.Codigo;
69
12. Obtener los nombres y apellidos de los empleados que trabajen en departamentos
cuyo presupuesto sea mayor de 60.000 Bs.
Solución 1 :
SELECT EMPLEADOS.Nombre, Apellidos
FROM EMPLEADOS INNER JOIN DEPARTAMENTOS
ON EMPLEADOS.Departamento = DEPARTAMENTOS.Codigo
AND DEPARTAMENTOS.Presupuesto > 60000;
Solución 2:
SELECT Nombre, Apellidos
FROM EMPLEADOS
WHERE Departamento IN (SELECT Codigo
FROM DEPARTAMENTOS
WHERE Presupuesto > 60000);
13. Obtener los datos de los departamentos cuyo presupuesto es superior al presupuesto
medio de todos los departamentos.
SELECT *
FROM DEPARTAMENTOS
WHERE Presupuesto > (SELECT AVG(Presupuesto)
FROM DEPARTAMENTOS);
14. Obtener los nombres de los departamentos que tienen más de dos empleados.
Solución 1 :
SELECT Nombre FROM DEPARTAMENTOS
WHERE Codigo IN ( SELECT Departamento
FROM EMPLEADOS
GROUP BY Departamento HAVING COUNT(*) > 2);
Solución 2 :
SELECT DEPARTAMENTOS.Nombre
FROM EMPLEADOS INNER JOIN DEPARTAMENTOS
ON Departamento = Codigo
GROUP BY DEPARTAMENTOS.Nombre
HAVING COUNT(*) > 2;
70
15. Añadir un nuevo departamento: ‘Calidad’, con presupuesto de 40.000 Bs. y código 11.
Añadir un empleado vinculado al departamento recién creado: ESTHER VAZQUEZ, DNI:
89267109.
UPDATE DEPARTAMENTOS
SET Presupuesto = Presupuesto * 0.9;
UPDATE EMPLEADOS
SET Departamento = 14
WHERE Departamento = 77;
18. Despedir a todos los empleados que trabajan para el departamento de informática
(código 14).
19. Despedir a todos los empleados que trabajen para departamentos cuyo presupuesto
sea superior a los 60.000 Bs.
71
Ejercicio 6 - Los almacenes [9]
Dado el siguiente Modelo Entidad Relación, se pide:
SELECT *
FROM ALMACENES;
2. Obtener todas las cajas cuyo contenido tenga un valor superior a 150 Bs.
SELECT *
FROM CAJAS
WHERE Valor > 150;
SELECT AVG(Valor)
FROM CAJAS;
6. Obtener los códigos de los almacenes en los cuales el valor medio de las cajas sea
superior a 150 Bs.
72
SELECT Almacen, AVG(Valor)
FROM CAJAS
GROUP BY Almacen
HAVING AVG(Valor) > 150;
7. Obtener el número de referencia de cada caja junto con el nombre de la ciudad en el que
se encuentra.
9. Obtener los códigos de los almacenes que están saturados (los almacenes donde el
número de cajas es superior a la capacidad).
SELECT Codigo
FROM ALMACENES
WHERE Capacidad < ( SELECT COUNT(*)
FROM CAJAS
WHERE Almacen = Codigo);
10. Obtener los números de referencia de las cajas que están en Bilbao
Solución 1 :
SELECT NumReferencia
FROM ALMACENES LEFT JOIN CAJAS
ON ALMACENES.Codigo = CAJAS.Almacen
WHERE Lugar = 'Bilbao';
Solución 2 :
SELECT NumReferencia
73
FROM CAJAS
WHERE Almacen IN (SELECT Codigo
FROM ALMACENES
WHERE Lugar = 'Bilbao');
12. Insertar una nueva caja, con número de referencia ‘H5RT’, con contenido ‘Papel’,
valor 200, y situada en el almacén 2.
14. Rebajar un 20 % el valor de todas las cajas cuyo valor sea superior al valor medio de
todas las cajas.
15. Eliminar todas las cajas cuyo valor sea inferior a 100 Bs.
74
Ejercicio 7 - Películas y salas [9]
Dado el siguiente Modelo Entidad Relación, se pide:
SELECT Nombre
FROM PELICULAS;
SELECT *
FROM PELICULAS
WHERE CalificacionEdad IS NULL;
SELECT *
FROM SALAS
WHERE Pelicula IS NULL;
SELECT *
FROM SALAS LEFT JOIN PELICULAS
ON SALAS.Pelicula = PELICULAS.Codigo;
75
6. Mostrar la información de todas las películas y, si se proyecta en alguna sala, mostrar
también la información de la sala.
SELECT *
FROM SALAS RIGHT JOIN PELICULAS
ON SALAS.Pelicula = PELICULAS.Codigo;
Solución 1 :
SELECT PELICULAS.Nombre
FROM SALAS RIGHT JOIN PELICULAS
ON SALAS.Pelicula = PELICULAS.Codigo
WHERE SALAS.Pelicula IS NULL;
Solución 2 :
SELECT Nombre FROM PELICULAS
WHERE Codigo NOT IN (SELECT Pelicula
FROM SALAS
WHERE Pelicula IS NOT NULL);
8. Añadir una nueva pelıcula ‘Uno, Dos, Tres’, para mayores de 7 años.
9. Hacer constar que todas las películas no calificadas han sido calificadas
‘no recomendables para menores de 13 años’.
10. Eliminar todas las salas que proyectan películas recomendadas para todos los públicos.
76
Ejercicio 8 - Los Directores [9]
Dado el siguiente Modelo Entidad Relación, se pide:
SELECT *
FROM DIRECTORES
WHERE DNIJefe IS NULL;
3. Mostrar el nombre y apellidos de cada director, junto con la capacidad del despacho en el
que se encuentra.
77
SELECT Numero, COUNT(DNI)
FROM DESPACHOS LEFT JOIN DIRECTORES
ON DESPACHOS.Numero = DIRECTORES.Despacho
GROUP BY Numero;
SELECT *
FROM DIRECTORES
WHERE DNIJefe IN (SELECT DNI
FROM DIRECTORES
WHERE DNIJefe IS NULL);
6. Mostrar los nombres y apellidos de los directores junto con los de su jefe.
SELECT Numero
FROM DESPACHOS
WHERE Capacidad < (SELECT COUNT(*)
FROM DIRECTORES
WHERE Despacho = Numero);
8. Añadir un nuevo director llamado Paco Pérez, DNI 28301700, sin jefe, y situado en el
despacho 124.
78
9. Asignar a todos los empleados de apellido Pérez un nuevo jefe con DNI 74568521.
10. Despedir a todos los directores, excepto a los que no tienen jefe.
79
Ejercicio 9 - Corretaje de Propiedades [10]
Dado el modelo relacional de una base de datos de una corredora de propiedades:
Telefonos(RUT, numero)
Nota: Las claves foráneas en los modelos relacionales presentes en este documento se representan en
cursiva y negrita
1. Los arrendatarios que arriendan la casa ubicada en la calle Carrera nº 1024, en el sector
Santiago.
80
4. Liste todas las personas de la base de datos. Las personas de la BD son los
arrendatarios y los dueños.
81
Ejercicio 10 - Piezas y Proveedores [9]
Dado el siguiente Modelo Entidad Relación, se pide:
SELECT Nombre
FROM PIEZAS;
SELECT *
FROM PROVEEDORES;
Solución 1:
SELECT PROVEEDORES.Nombre
FROM PROVEEDORES INNER JOIN SUMINISTRA
ON PROVEEDORES.Id = SUMINISTRA.IdProveedor
AND SUMINISTRA.CodigoPieza = 1;
Solución 2:
SELECT Nombre
FROM PROVEEDORES
WHERE Id IN (SELECT IdProveedor
FROM SUMINISTRA
WHERE CodigoPieza = 1);
5. Obtener los nombres de las piezas suministradas por el proveedor cuyo código es
HAL. Solución 1:
SELECT PIEZAS.Nombre
FROM PIEZAS INNER JOIN SUMINISTRA
ON PIEZAS.Codigo = SUMINISTRA.CodigoPieza
AND SUMINISTRA.IdProveedor = 'HAL';
82
Solución 2:
SELECT Nombre
FROM PIEZAS
WHERE Codigo IN (SELECT CodigoPieza
FROM SUMINISTRA
WHERE IdProveedor = 'HAL');
Solución 3:
SELECT Nombre
FROM PIEZAS
WHERE EXISTS (SELECT *
FROM SUMINISTRA
WHERE IdProveedor = 'HAL'
AND CodigoPieza = PIEZAS.Codigo);
6. Obtener los nombres de los proveedores que suministran las piezas más caras,
indicando el nombre de la pieza y el precio al que la suministran.
10. Hacer constar en la base de datos que la empresa ”Susan Calvin Corp.”(RBT) ya no
va a suministrarnos clavos (código 4)
83
Ejercicio 11 - Departamentos y Empleados [10]
Dado el DDL de la base de datos de hospitales:
CREATE TABLE temple1 (
nuempl CHAR(6) NOT NULL,
nombre CHAR(12) NOT
NULL,
inicial CHAR(1) NOT NULL,
apellido CHAR(15) NOT
NULL, dept CHAR(3) NOT
NULL,
tlfn CHAR(4),
feching DATE NOT NULL,
codtra SMALLINT NOT NULL,
niveduc SMALLINT NOT NULL,
sexo CHAR(1) NOT NULL,
fechnac DATE NOT NULL,
salario DECIMAL(9,2) NOT NULL );
1. Obtener una lista de todas las empleadas de los departamentos que empiecen por D
o por E. La lista anterior debe contener información sobre el número de personal,
nombre, apellido y número de teléfono.
2. Obtener un listado de todos los empleados (nombre y apellido) que ganan más de
2000 Bs al mes y que entraron en la compañía después del 1 de Enero de 1975.
También se quiere la información correspondiente a su código de trabajo y al número de
personal de sus directores.
3. Obtener una lista con el apellido, número de departamento y salario mensual de los
empleados de los departamentos ‘A00’, ‘B01’, ‘C01’ y ‘D01’. La salida se quiere en
orden descendente de salario dentro de cada departamento.
84
4. Se pide una lista que recupere el salario medio de cada departamento junto con el
número de empleados que tiene. El resultado no debe incluir empleados que tengan
un código de trabajo mayor que 54, ni departamentos con menos de tres empleados.
Se quiere ordenada por número de departamento.
Solución 1:
SELECT salario, numempl
FROM (SELECT AVG(salario) as salario, COUNT(*) AS numempl, dept
FROM temple1
WHERE codtra <= 54
GROUP BY dept ) AS result
WHERE numempl > 2
ORDER BY dept ASC;
Solución 2:
SELECT dept, AVG(salario), COUNT(*)
FROM temple1
WHERE codtra <= 54
GROUP BY dept
HAVING COUNT(*) > 2
ORDER BY dept;
5. Seleccionar todos los empleados de los departamentos ‘D11’ y ‘E11’ cuyo primer apellido
empiece por S.
SELECT *
FROM temple1
WHERE dept IN ( 'D11', 'E11' )
AND apellido LIKE 'S%';
Solución 1:
SELECT nombre, apellido, feching
FROM temple1
WHERE nuempl IN (SELECT numdirec FROM tdepar2);
Solución 2:
SELECT nuempl, nombre, apellido, feching
FROM temple1 , tdepar2
WHERE temple1.nuempl = tdepar2.numdirec
ORDER BY nuempl;
85
7. Obtener un listado de las mujeres de los departamentos que empiecen por D y por
E cuyo nivel de educación sea superior a la media; en este caso también ordenados
por número de personal.
8. Seleccionar todos los empleados cuyo nombre sea igual al de algunas personas del
departamento D21 y cuyo código de trabajo sea diferente de todos los del E21 (la lista
debe contener el número de personal, nombre, apellido, departamento y código de
trabajo).
Solución 1:
SELECT *
FROM temple1
WHERE nombre IN (SELECT nombre
FROM temple1
WHERE dept = 'D21')
AND codtra NOT IN (SELECT codtra
FROM temple1
WHERE dept = 'E21')
AND dept <> 'D21';
Solución 2:
SELECT nuempl, nombre, apellido, dept, codtra
FROM temple1
WHERE nombre = ANY (SELECT nombre
FROM temple1
WHERE dept = 'D21')
AND codtra <> ALL ( SELECT codtra
FROM temple1 WHERE dept = 'E21')
AND dept <> 'D21';
9. Listar los empleados que no sean directores (la información que debe aparecer es
el número de personal, apellido y departamento).
SELECT *
FROM temple1
WHERE nuempl NOT IN (SELECT numdirec FROM tdepar2);
86
10. Seleccionar parejas de empleados (de sexo opuesto) que hayan nacido el mismo día
(con información acerca de apellido y fecha de nacimiento).
11. Obtener un listado de todos los empleados que pertenecen al mismo departamento
que Tomás Soler.
SELECT *
FROM temple1
WHERE dept = (SELECT dept
FROM temple1
WHERE nombre = 'TOMAS'
AND apellido = 'SOLER');
87
Ejercicio 12 - Control de Stock y facturación [11]
Dado el siguiente modelo relacional de una base de datos, se pide:
PROVINCIAS( CODPRO, NOMBRE)
PUEBLOS( CODPUE, NOMBRE, CODPRO)
CLIENTES( CODCLI, NOMBRE, DIRECCION, CODPOSTAL, CODPUE)
VENDEDORES( CODVEN, NOMBRE, DIRECCION, CODPOSTAL, CODPUE, CODJEFE)
ARTICULOS( CODART, DESCRIP, PRECIO, STOCK, STOCK_MIN )
FACTURAS( CODFAC, FECHA, CODCLI, CODVEN, IVA, DTO )
LINEAS_FAC( CODFAC, LINEA, CANT, CODART, PRECIO, DTO )
Nota: Las claves foráneas en los modelos relacionales presentes en este documento se representan en
cursiva y negrita.
SELECT *
FROM provincias;
88
6. Mostrar el código y nombre de aquellas provincias cuyo código es menor a 20.
7. Mostrar los distintos tipos de descuento de aplicados por los vendedores que cuyos
códigos no superan el valor 50.
8. Mostrar el código y descripción de aquellos artículos cuyo stock es igual o supera los 50
unidades.
9. Mostrar el código y fechas de las facturas con IVA 16 y que pertenecen al cliente de
código 100.
10. Mostrar el código y fechas de las facturas con IVA 16 o con descuento 20 y que
pertenecen al cliente de código 100.
11. Mostrar el código de la factura y el número de línea de las facturas cuyas líneas
superan 100 Bs sin considerar descuentos ni impuestos.
89
12. Importe medio por factura, sin considerar descuentos ni impuestos. El importe de una
factura se calcula sumando el producto de la cantidad por el precio de sus líneas.
13. Stock medio, máximo, y mínimo de los artículos que contienen la letra A en la segunda
posición de su descripción y cuyo stock mínimo es superior a la mitad de su stock
actual.
14. Número de facturas para cada año. Junto con el año debe aparecer el número de
facturas de ese año.
15. Número de facturas de cada cliente, pero sólo se deben mostrar aquellos clientes que
tienen más de 15 facturas.
16. Cantidades totales vendidas para cada artículo cuyo código empieza por “F”. La cantidad
total vendida de un artículo se calcula sumando las cantidades de todas sus líneas de
factura.
17. Código de aquellos artículos de los que se ha facturado más de 6000 euros.
SELECT codart
FROM lineas_fac
GROUP BY codart
HAVING SUM(cant * precio) > 6000;
90
18. Número de facturas de cada uno de los clientes cuyo código está entre 241 y 250, con
cada IVA distinto que se les ha aplicado. En cada línea del resultado se debe mostrar
un código de cliente, un IVA y el número de facturas de ese cliente con ese IVA.
19. Vendedores y clientes cuyo nombre coincide (vendedores que a su vez han
comprado algo a la empresa)
SELECT v.nombre
FROM vendedores v
INTERSECT
SELECT c.nombre
FROM clientes e;
20. Creación de una vista que muestre únicamente los códigos postales de los clientes que
inicien con el número 12.
21. Mostrar el código y el nombre de los clientes de Castellón (posee código 12) que han
realizado facturas con vendedores de más de dos provincias distintas. El resultado
debe quedar ordenado ascendentemente respecto del nombre del cliente.
91
Ejercicio 13 - Pedidos [12]
Dado el DDL de la base de datos, se pide:
CREATE TABLE EMPLEADOS(
CREATE TABLE PROVEEDORES(
EMPLEADOID NUMBER(8) ,
PROVEEDORID NUMBER(8) ,
NOMBRE VARCHAR(30),
NOMBREPROV VARCHAR(50) NOT NULL,
APELLIDO VARCHAR(30),
CONTACTO VARCHAR(50) NOT NULL,
FECHA_NAC DATE,
CELUPROV VARCHAR(12),
REPORTA_A NUMBER(8),
FIJOPROV VARCHAR(12),
EXTENSION NUMBER(8),
CONSTRAINT PK_PROVEEDORES PRIMARY
CONSTRAINT PK_EMPLEADOS PRIMARY KEY
KEY(PROVEEDORID ) );
(EMPLEADOID));
ALTER TABLE ORDENES ADD CONSTRAINT FK_ORDENES_CLIEN_ORD_CLIENTES FOREIGN KEY (CLIENTEID) REFERENCES CLIENTES
(CLIENTEID);
ALTER TABLE ORDENES ADD CONSTRAINT FK_ORDENES_EMPLE_ORD_EMPLEADO FOREIGN KEY (EMPLEADOID) REFERENCES
EMPLEADOS (EMPLEADOID);
ALTER TABLE PRODUCTOS ADD CONSTRAINT FK_PRODUCTO_CATE_PROD_CATEGORI FOREIGN KEY (CATEGORIAID) REFERENCES
CATEGORIAS (CATEGORIAID);
92
ALTER TABLE PRODUCTOS ADD CONSTRAINT FK_PRODUCTO_PROV_PROD_PROVEEDO FOREIGN KEY (PROVEEDORID) REFERENCES
PROVEEDORES (PROVEEDORID);
ALTER TABLE EMPLEADOS ADD CONSTRAINT FK_EMPLEADO_REPORTA FOREIGN KEY (REPORTA_A) REFERENCES EMPLEADOS
(EMPLEADOID);
UPDATE PRODUCTOS
SET PRECIOUNIT = (PRECIOUNIT * 0.1) + PRECIOUNIT
WHERE CATEGORIAID = (SELECT CATEGORIAID
FROM CATEGORIAS
WHERE NOMBRECAT = 'CARNICOS');
2. Actualizar el teléfono celular del proveedor cuyo contacto es MANUEL ANDRADE, con
el valor 099010291
UPDATE PROVEEDORES
SET CELUPROV = '0990101291'
WHERE CONTACTO = 'MANUEL ANDRADE';
5. Mostrar la suma total de cada tipo de producto pedidos en todas las órdenes.
93
6. Mostrar el número de órdenes atendidas por cada empleado, incluidos los que tienen 0
órdenes.
94
Ejercicio 14 - Locales Nocturnos
Se pide escribir los comandos SQL (DDL) que permitan la creación de las tablas
anteriores teniendo en cuenta las siguientes restricciones:
● Todos los valores son de tipo carácter excepto los campos FECHA_APERTURA
(fecha) , CANTIDAD, PRECIO y COD_LOCALIDAD (numéricos).
● Los únicos campos que no son obligatorios son los campos DOMICILIO.
● Los valores del campo horario sólo pueden ser HOR1, HOR2 y HOR3.
● No es posible dar de alta EXISTENCIAS a precio 0.
● El campo función de la tabla PUB_EMPLEADO sólo puede tener los valores
CAMARERO, SEGURIDAD, LIMPIEZA.
● Se ha de mantener la integridad referencial entre las tablas.
● Las claves primarias vienen marcadas con el símbolo #.
95
CREATE TABLE pub (
cod_pub VARCHAR(5) NOT NULL,
nombre VARCHAR(60) NOT NULL,
licencia_fiscal VARCHAR(60) NOT NULL,
domicilio VARCHAR(60),
fecha_apertura DATE NOT NULL,
horario VARCHAR(10) NOT NULL,
cod_localidad NUMBER(5) NOT NULL,
CONSTRAINT pk_pub PRIMARY KEY (cod_pub),
CONSTRAINT fk_pub_localidad FOREIGN KEY (cod_localidad) REFERENCES
localidad (cod_localidad),
CONSTRAINT ck_horario CHECK (horario IN ('HOR1', 'HOR2', 'HOR3'))) ;
96
CREATE TABLE pub_empleado (
cod_pub VARCHAR(5) NOT NULL,
dni_empleado VARCHAR(8) NOT NULL,
funcion VARCHAR(9) NOT NULL,
CONSTRAINT pk_pub_empleado PRIMARY KEY (cod_pub, dni_empleado,
funcion),
CONSTRAINT fk_pubemple_pub FOREIGN KEY (cod_pub) REFERENCES
pub(cod_pub),
CONSTRAINT fk_pubemple_empleado FOREIGN KEY (dni_empleado) REFERENCES
empleado (dni_empleado),
CONSTRAINT ck_funcion CHECK (funcion IN ('CAMARERO','SEGURIDAD',
'LIMPIEZA')) ;
97
Ejercicio 15 - Empleados de una empresa
Dado el DDL de la base de datos, se pide:
98
2. Dos DEPARTAMENTOS no se llaman igual. Dos TRABAJOS tampoco.
6. Crear una nueva tabla llamada INFORMACIÓN UNIVERSITARIA que tenga el NOMBRE y
los dos APELLIDOS (en un solo atributo) de todos los EMPLEADOS junto con la
UNIVERSIDAD donde estudiaron.
99
7. Crear una vista llamada NOMBRE_EMPLEADOS con el NOMBRE y los dos APELLIDOS
(en un solo atributo) de todos los EMPLEADOS que son de Vargas.
9. Crear otra vista sobre la anterior llamada INFORMACION_ACTUAL que dispone de toda
la información de INFORMACION_EMPLEADOS junto con el SALARIO que está cobrando
en este momento
10
Ejercicio 16 - Departamentos y empleados [13]
Dado el siguiente modelo relacional de una base de datos de una agencia de viajes
Nota: Las claves foráneas en los modelos relacionales presentes en este documento se representan en
cursiva y negrita.
SELECT *
FROM Empleado;
SELECT *
FROM Departamento;
SELECT *
FROM Empleado
WHERE cargoE = 'Secretaria';
SELECT *
FROM Empleado
WHERE cargoE = 'Vendedor'
ORDER BY nomEmp;
10
7. Obtener el nombre y cargo de todos los empleados, ordenado por salario.
8. Obtener el nombre y cargo de todos los empleados, ordenado por cargo y por salario.
9. Obtener el nombre y cargo de todos los empleados, en orden inverso por cargo.
10
Ejercicio 17 - Empleados de una empresa [14]
Dada la siguiente base de datos relacional de una empresa, se pide:
SELECT nombre
FROM EMPLEADO
ORDER BY nombre DESC;
3. Listar los nombres de los empleados cuyo nombre termine con la letra ‘o’.
SELECT nombre
FROM EMPLEADO
WHERE nombre LIKE '%o';
10
4. Seleccionar el nombre, el oficio y salario de los empleados que la localización
donde trabajan es San Felipe.
5. Seleccionar el nombre, salario y localidad donde trabajan los empleados que tengan un
salario entre 10000 y 13000.
7. Mostrar el nombre, salario y nombre del departamento de los empleados que tengan
el mismo oficio que ‘Leonel Alfonso Esquivel’.
8. Mostrar el nombre, salario y nombre del departamento de los empleados que tengan
el mismo oficio que “Castillo Montes Luis” y que no tengan comisión.
10
9. Mostrar los datos de los empleados que trabajan en el departamento de contabilidad,
ordenados por nombre.
SELECT *
FROM EMPLEADO, DEPARTAMENTO
WHERE EMPLEADO.dept_no = DEPARTAMENTO.dept_no
AND nombre_depto = 'Contabilidad'
ORDER BY nombre;
10. Nombre de los empleados que trabajan en Caracas y cuyo oficio sea analista
o empleado.
SELECT nombre
FROM EMPLEADO, DEPARTAMENTO
WHERE EMPLEADO.depto_no = Departamento.depto_no
AND localizacion = 'Caracas'
AND oficio IN ('Analista','Empleado');
SELECT AVG(salario)
FROM EMPLEADO;
SELECT MAX(salario)
FROM EMPLEADO
WHERE depto_no = 10;
SELECT MIN(salario)
FROM EMPLEADO, DEPARTAMENTO
WHERE nombre_depto = 'Ventas'
AND EMPLEADO.dept_no = DEPARTAMENTO.dept_no;
SELECT AVG(salario)
FROM EMPLEADO , DEPARTAMENTO
WHERE EMPLEADO.dept_no = DEPARTAMENTO.dept_no
AND nombre_depto = 'Contabilidad';
10
15. ¿Cuántos empleados hay en el departamento número 10?
SELECT COUNT(*)
FROM EMPLEADO
WHERE depto_no = 10;
SELECT COUNT(*)
FROM EMPLEADO, DEPARTAMENTO
WHERE nombre_depto = 'VENTAS';
SELECT COUNT(*)
FROM EMPLEADO
WHERE comision IS NULL;
18. Visualizar cuántos nombres de los empleados empiezan por la letra ‘A’.
SELECT COUNT(*)
FROM EMPLEADO
WHERE nombre LIKE 'A%';
21. Mostrar los datos de los empleados cuyo salario sea mayor que la media de todos
los salarios.
SELECT *
FROM EMPLEADO
WHERE salario > (SELECT AVG(salario)
FROM EMPLEADO);
10
22. Seleccionar el nombre del empleado que tiene máximo salario.
SELECT nombre
FROM EMPLEADO
WHERE salario = (SELECT MAX(salario) FROM EMPLEADO);
23. Mostrar el nombre del empleado que tiene el salario más bajo.
SELECT nombre
FROM EMPLEADO
WHERE salario = (SELECT MIN(salario) FROM EMPLEADO);
24. Mostrar los datos del empleado que tiene el salario más alto en el departamento de
‘VENTAS’.
SELECT nombre
FROM EMPLEADO,DEPARTAMENTO
WHERE EMPLEADO.depto_no = DEPARTAMENTO.depto_no
AND nombre_depto = 'VENTAS'
AND salario = (SELECT MAX(salario)
FROM EMPLEADO,DEPARTAMENTO
WHERE EMPLEADO.depto_no = DEPARTAMENTO.depto_no
AND nombre_depto = 'VENTAS');
26. Mostrar los departamentos que trabajando más de dos personas de la misma profesión.
10
28. Insertar en la tabla DEPARTAMENTO un departamento cuyo número sea 50, de
nombre ‘GENERAL’ y cuya localización sea ‘Caracas’.
30. Insertar en la tabla PRUEBA los datos de los empleados que pertenecen al
departamento número 30.
UPDATE EMPLEADO
SET salario = salario * 2
WHERE depto_no = 30;
33. Cambiar todos los empleados del departamento número 30 al departamento número 20.
UPDATE EMPLEADO
SET depto_no = 20
WHERE depto_no = 30;
UPDATE EMPLEADO
SET salario = salario * 1.1
WHERE depto_no = 10;
UPDATE EMPLEADO
SET localizacion = 'Maracaibo' WHERE depto_no = 10;
10
36. Igualar el salario de ‘Rodriguez Jose’ al salario de ‘Ruiz Leonel Alfonso’, de la tabla
PRUEBA.
UPDATE EMPLEADO
SET salario = (SELECT salario FROM PRUEBA
WHERE nombre = 'Ruiz Leonel Alfonso')
WHERE nombre = 'Rodriguez Jose';
38. En la tabla EMPELADO borrar todos los empleados que sean del departamento 20 y
sean ‘ANALISTAS’.
39. Borrar de la tabla EMPLEADO todos los empleados que no tengan comisión.
10
Ejercicio 18 - Libros [15]
Dado el siguiente modelo relacional, se pide:
Nota: Las claves foráneas en los modelos relacionales presentes en este documento se representan en
cursiva y negrita.
SELECT *
FROM AUTOR;
SELECT nombre
FROM ESTUDIANTE
WHERE carrera = 'Informatica';
SELECT nombre
FROM ESTUDIANTE
WHERE nombre LIKE 'G%';
5. Listar los nombre de los autores del libro Base de Datos I, utilizando subconsulta.
SELECT A.nombre
FROM AUTOR A, LIBAUTOR L
WHERE A.IDAUTOR = L.IDAUTOR
AND L.IDLIBRO IN (SELECT IDLIBRO
FROM LIBRO WHERE titulo = 'Base de Datos I');
11
6. ¿ Qué autores son de nacionalidad francesa o venezolana ?
SELECT *
FROM AUTOR
WHERE nacionalidad IN ('Francesa', 'Venezolana');
SELECT *
FROM LIBRO
WHERE area <> 'Informatica';
SELECT *
FROM LIBRO
WHERE idlibro IN (SELECT P.idlibro
FROM PRESTAMO P, ESTUDIANTE E
WHERE P.idlector = E.idlector
AND E.nombre = 'Pedro Ruiz');
SELECT nombre
FROM ESTUDIANTE
WHERE edad = (SELECT MIN(edad)
FROM ESTUDIANTE );
10. Utilizando subconsulta, listar los estudiantes a los que se les prestó libros del área de
Bases de Datos.
SELECT nombre
FROM ESTUDIANTE
WHERE idlector IN (SELECT P.idlector
FROM PRESTAMO P, LIBRO L
WHERE P.idlibro = L.idlibro
AND L.area = 'Bases de Datos');
SELECT *
FROM LIBRO
WHERE editorial = 'UCAB';
11
12. Listar los libros que son del autor Mario Benedetti.
SELECT *
FROM LIBRO L , AUTOR A , LIBAUTOR LA
WHERE L.idlibro = LA.idlibro
AND LA.idautor = A.idautor
AND A.nombre = 'Mario Benedetti';
13. Listar los títulos de los libros que debían devolverse el 01-09-2019.
SELECT titulo
FROM LIBRO
WHERE idlibro IN (SELECT idlibro
FROM PRESTAMO
WHERE fechadevolucion = '01-09-2019'
AND devuelto = 'NO' );
15. Listar los datos de los estudiantes cuya edad es mayor al promedio de la edad de
los estudiantes.
SELECT *
FROM ESTUDIANTE
WHERE edad > (SELECT AVG(edad)
FROM ESTUDIANTE);
11
Ejercicio 19 - Juegos de la NBA
Dado el siguiente modelo relacional, se pide:
Nota: Las claves foráneas en los modelos relacionales presentes en este documento se representan en
cursiva y negrita.
SELECT NOMBRE
FROM JUGADORES
ORDER BY NOMBRE;
2. Mostrar el nombre de los jugadores cuya posición contenga la letra C y con más de
200 libras de peso, ordenados alfabéticamente.
SELECT NOMBRE
FROM JUGADORES
WHERE POSICION LIKE '%C%'
AND PESO > 200 ORDER BY NOMBRE;
SELECT NOMBRE
FROM EQUIPOS
ORDER BY NOMBRE;
4. Mostrar el nombre de los equipos cuya conferencia sea este, ordenado por nombre.
SELECT NOMBRE
FROM EQUIPOS
WHERE CONFERENCIA = 'ESTE'
ORDER BY NOMBRE;
11
5. Mostrar los equipos donde su ciudad empieza por C, ordenado por nombre.
SELECT NOMBRE
FROM EQUIPOS
WHERE CIUDAD LIKE 'C%'
ORDER BY NOMBRE;
6. Mostrar todos los jugadores y su equipo ordenado por nombre del equipo.
7. Mostrar todos los jugadores del equipo “Raptors” ordenado por nombre de jugador.
SELECT J.NOMBRE
FROM JUGADORES J
WHERE J.NOMBRE_EQUIPO = 'RAPTORS'
ORDER BY J.NOMBRE;
SELECT E.PUNTOS_POR_PARTIDO
FROM ESTADISTICAS E, JUGADORES J
WHERE E.JUGADOR = J.CODIGO
AND J.NOMBRE = 'LUIS RUIZ';
SELECT E.PUNTOS_POR_PARTIDO
FROM ESTADISTICAS E, JUGADORES J
WHERE E.JUGADOR = J.CODIGO
AND J.NOMBRE = 'RIU MORALES'
AND TEMPORADA = '04/05';
10. Mostrar el total de puntos de cada jugador en toda su carrera, ordenado por nombre del
jugador.
11
11. Mostrar el número de jugadores de cada equipo.
SELECT T.NOMBRE
FROM ( SELECT J.NOMBRE, SUM(E.PUNTOS_POR_PARTIDOS) AS PUNTOS
FROM JUGADORES J, ESTADISTICAS E
WHERE J.CODIGO = E.JUGADOR
GROUP BY J.NOMBRE
ORDER BY J.NOMBRE) T
WHERE T.PUNTOS = (SELECT MAX(T2.PUNTOS)
FROM (SELECT J.NOMBRE,
SUM(E.PUNTOS_POR_PARTIDOS) AS PUNTOS
FROM JUGADORES J, ESTADISTICAS E
WHERE J.CODIGO = E.JUGADOR
GROUP BY J.NOMBRE) T2);
13. Mostrar el nombre del equipo, conferencia y división del jugador más alto de la NBA.
14. Mostrar la suma de los puntos por partido de todos los jugadores venezolanos
que juegan en equipos de la ciudad de ‘Los Ángeles’.
11
15. Mostrar la media de puntos en partidos de los equipos de la división Pacific.
SELECT AVG(PUNTOS)
FROM (SELECT SUM(PUNTOS_LOCAL) AS PUNTOS
FROM PARTIDOS
WHERE EQUIPO_LOCAL IN (SELECT NOMBRE
FROM EQUIPOS
WHERE DIVISION = 'PACIFIC')
UNION
SELECT SUM(PUNTOS_VISITANTE) AS PUNTOS
FROM PARTIDOS
WHERE EQUIPO_VISITANTE IN (SELECT NOMBRE
FROM EQUIPOS
WHERE DIVISION = 'PACIFIC')) T;
16. Mostrar el partido o partidos (equipo local, equipo visitante y diferencia) con mayor
diferencia de puntos.
17. Mostrar los puntos de cada equipo en los partidos, tanto de local como de visitante. Crear
una vista.
11
18. Mostrar quien gana en cada partido (código, equipo local, equipo visitante, equipo
ganador), en caso de empate será null. Crear una vista.
11
Ejercicio 20 - Proveedores y componentes [16]
Dado las siguientes tablas, se pide:
SELECT *
FROM artículos
WHERE ciudad = 'CACERES';
2. Obtener todos los valores de P# para los proveedores que abastecen el artículo T1.
SELECT DISTINCT p#
FROM envios
WHERE t# = 'T1';
11
4. Obtener de la tabla de artículos los valores de T# y CIUDAD donde el nombre de la
ciudad acaba en D o contiene al menos una E.
5. Obtener los valores de P# para los proveedores que suministran para el artículo T1 el
componente C1.
SELECT p#
FROM envios
WHERE t# = 'T1'
AND c# = 'C1';
SELECT tnombre
FROM artículos a, envios e
WHERE e.p# = 'P1'
AND e.t# = a.t#
ORDER BY tnombre;
SELECT DISTINCT c#
FROM envios
WHERE t# IN ( SELECT t#
FROM artículos
WHERE ciudad = 'MADRID');
8. Obtener todos los valores de C# de los componentes tales que ningún otro
componente tenga un valor de peso inferior.
SELECT c#
FROM componentes
WHERE peso = (SELECT MIN(peso)
FROM componentes );
11
9. Obtener los valores de P# para los proveedores que suministren los artículos T1 y
T2.
SELECT p# AS codigo
FROM envios
WHERE t# = 'T1'
INTERSECT
SELECT p# AS codigo
FROM envios
WHERE t# = 'T2';
10. Obtener los valores de P# para los proveedores que suministran para un artículo
de SEVILLA o MADRID un componente ROJO.
SELECT p#
FROM envios e, componentes c, artículos a
WHERE e.c# = c.c#
AND e.t# = a.t#
AND c.color = 'ROJO'
AND a.ciudad IN ('SEVILLA', 'MADRID');
SELECT c#
FROM envios
WHERE t# IN (SELECT t#
FROM artículos
WHERE ciudad = 'SEVILLA')
AND p# IN (SELECT p#
FROM proveedores
WHERE ciudad = 'SEVILLA');
12. Obtener los valores de T# para los artículos que usan al menos un componente que se
puede obtener con el proveedor P1.
SELECT DISTINCT t#
FROM envios
WHERE c# IN ( SELECT DISTINCT c#
FROM envios
WHERE p# = 'P1' );
12
13. Obtener todas las ternas (CIUDAD, C#, CIUDAD) tales que un proveedor de la
primera ciudad suministre el componente especificado para un artículo montado en la
segunda ciudad.
14. Repetir el ejercicio anterior pero sin recuperar las ternas en los que los dos valores de
ciudad sean los mismos.
16. Para cada artículo y componente suministrado obtener los valores de C#, T#
y la cantidad total correspondiente.
12
17. Obtener los valores de T# de los artículos abastecidos al menos por un proveedor
que no viva en MADRID y que no esté en la misma ciudad en la que se monta
el artículo.
18. Obtener los valores de P# para los proveedores que suministran al menos un
componente suministrado al menos por un proveedor que suministra al menos un
componente ROJO.
SELECT DISTINCT p#
FROM envios
WHERE c# IN (SELECT c#
FROM envios
WHERE p# IN ( SELECT e.p#
FROM envios e , componentes c
WHERE c.color = 'ROJO'
AND c.c# = e.c# ) );
19. Obtener los identificadores de artículos, T#, para los que se ha suministrado algún
componente del que se haya suministrado una media superior a 320 artículos.
SELECT DISTINCT t#
FROM envios
WHERE c# IN ( SELECT c#
FROM envios
GROUP BY c#
HAVING AVG(cantidad) > 320 );
12
20. Seleccionar los identificadores de proveedores que hayan realizado algún envío con
Cantidad mayor que la media de los envíos realizados para el componente a que
corresponda dicho envío.
SELECT DISTINCT p#
FROM envios a
WHERE cantidad > (SELECT AVG(cantidad)
FROM envios b
WHERE b.c# = a.c# );
SELECT c#
FROM envios
WHERE t# = 'T2'
AND p# = 'P2';
22. Seleccionar todos los datos de los envíos realizados de componentes cuyo color
no sea 'ROJO'.
SELECT e.*
FROM envios e, componentes c
WHERE e.c# = c.c#
AND color <> 'ROJO';
23. Seleccionar los identificadores de componentes que se suministren para los artículos 'T1'
y 'T2'.
SELECT c#
FROM envios
WHERE t# = 'T1'
INTERSECT
SELECT c#
FROM envios
WHERE t# = 'T2';
12
24. Seleccionar el identificador de proveedor y el número de envíos de componentes de
color 'ROJO' llevados a cabo por cada proveedor.
26. Seleccionar los datos de envío y nombre de ciudad de aquellos envíos que cumplan que
el artículo, proveedor y componente son de la misma ciudad.
27. Seleccionar los nombres de los componentes que son suministrados en una cantidad
total superior a 500.
12
28. Seleccionar los identificadores de proveedores que residan en Sevilla y no
suministren más de dos artículos distintos.
SELECT p#
FROM proveedores
WHERE ciudad = 'SEVILLA'
MINUS
SELECT p#
FROM envios
GROUP BY p#
HAVING COUNT(DISTINCT t#) > 2;
29. Seleccionar los identificadores de artículos para los cuales todos sus componentes se
fabrican en una misma ciudad.
SELECT t#
FROM envios e, componentes c
WHERE e.c# = c.c#
GROUP BY t#
HAVING COUNT(DISTINCT ciudad) = 1 ;
30. Seleccionar los identificadores de artículos para los que se provean envíos de todos los
componentes existentes en la base de datos.
SELECT t#
FROM Envíos
GROUP BY t#
HAVING COUNT(DISTINCT c#) = ( SELECT COUNT(*)
FROM Componentes) ;
31. Seleccionar los códigos de proveedor y artículo que suministran al menos dos
componentes de color 'ROJO'.
SELECT p#, t#
FROM envios e,componentes c
WHERE e.c# = c.c#
AND c.color = 'ROJO'
GROUP BY p#, t#
HAVING COUNT (*) > 1;
12
Ejercicio 21 -Venta de Productos [18]
Dado el siguiente modelo relacional de una base de datos, se pide:
Nota: Las claves foráneas en los modelos relacionales presentes en este documento se representan en
cursiva y negrita.
12
5. Sobre la consulta 3, obtener solo el importe total para las facturas mayores iguales a 2 y
menores iguales a 5 y solo para el producto código c.
6. Sobre la consulta 3, obtener solo el importe total para los registros cuyo importe total sea
mayor a 200.
8. Obtener un listado de las facturas realizadas cuya cantidad sea mayor igual a 15
especificando número de factura, nombre del producto y cantidad vendida.
9. Obtener un listado de las facturas realizadas indicando número de factura, nombre del
cliente, nombre del producto, cantidad y precio y el importe total.
12
11. Obtener la cantidad total de unidades vendidas del producto c.
12. Cantidad de unidades vendidas por producto, indicando la descripción del producto,
ordenado de mayor a menor por las cantidades vendidas.
13. Cantidad de unidades vendidas por producto, indicando la descripción del producto,
ordenado alfabéticamente por nombre de producto para los productos que vendieron
más de 30 unidades.
14. Obtener cuantas compras (1 factura = 1 compra) realizo cada cliente indicando el código y
nombre del cliente ordenado de mayor a menor.
15. Promedio de unidades vendidas por producto, indicando el código del producto para el
cliente 1.
12
Ejercicio 22 - Oficina ferretera [17]
Dado el siguiente modelo relacional, se pide:
Nota: Las claves foráneas en los modelos relacionales presentes en este documento se representan en
cursiva y negrita.
4. Muestra las ventas de cada oficina , ordenadas por orden alfabético de región y dentro
de cada región por ciudad.
12
5. Lista las oficinas clasificadas por región y dentro de cada región por ganancia (ventas -
objetivo) de modo que las de mayor ganancia aparezcan las primeras.
SELECT nombre
FROM empleado
WHERE oficina = 12
AND edad > 30;
8. Lista las oficinas cuyas ventas estén por debajo del 80% de su objetivo.
SELECT oficina
FROM oficina
WHERE ventas < objetivo * 0.8;
9. Lista los empleados cuyas ventas estén comprendidas entre 100.000 y 500.00
13
12. Lista los empleados cuyo nombre empiece por Luis.
13. Obtener una lista de todos los productos, indicando para cada uno su idfab,
idproducto, descripción, precio y precio con IVA (es el precio aumentado en un 16%).
14. De cada pedido se quiere saber el número de pedido, fab, producto, cantidad, precio
unitario e importe.
15. Obtener las oficinas ordenadas por orden alfabético de región y dentro de cada región
por ciudad, si hay más de una oficina en la misma ciudad, aparecerá primero la que tenga
el número de oficina mayor.
SELECT *
FROM oficinas
ORDER BY region, ciudad, oficina DESC;
SELECT *
FROM pedidos
ORDER BY fechapedido;
17. Listar las cuatro líneas de pedido más caras (las de mayor importe).
SELECT TOP 4 *
FROM pedidos
ORDER importe DESC;
13
18. Obtener de los pedidos: fab, producto, cantidad, precio unitario e importe, pero sacando
únicamente las 5 líneas de pedido de menor precio unitario.
19. Listar los números de los empleados que tienen una oficina asignada.
SELECT numemp
FROM empleados
WHERE oficina IS NOT NULL;
SELECT oficina
FROM oficinas
WHERE dir IS NULL;
21. Listar los datos de las oficinas de las regiones del norte y del este (tienen que aparecer
primero las del norte y después las del este).
SELECT *
FROM oficinas
WHERE region IN ('norte','este')
ORDER BY region DESC;
SELECT *
FROM empleados
WHERE nombre LIKE 'Julia%';
SELECT *
FROM productos
WHERE idproducto LIKE '%x';
13
24. Listar las oficinas del este indicando para cada una de ellas su número, ciudad, números y
nombres de sus empleados. Hacer una versión en la que aparecen sólo las que tienen
empleados, y hacer otra en las que aparezcan las oficinas del este que no tienen
empleados.
25. Listar los pedidos mostrando su número, importe, nombre del cliente, y el límite de
crédito del cliente correspondiente (todos los pedidos tienen cliente y representante).
26. Listar los datos de cada uno de los empleados, la ciudad y región en donde trabaja.
27. Listar las oficinas con objetivo superior a 600.000 Bs. indicando para cada una de ellas
el nombre de su director.
13
28. Listar los pedidos superiores a 25.000 Bs, incluyendo el nombre del empleado que
tomó el pedido y el nombre del cliente que lo solicitó.
29. Hallar los empleados que realizaron su primer pedido el mismo día en que
fueron contratados.
SELECT empleados.*
FROM empleados INNER JOIN pedidos
ON pedidos.rep = empleados.numemp
WHERE fechapedido = contrato;
30. Listar los empleados con una cuota superior a la de su jefe; para cada empleado
sacar sus datos y el número, nombre y cuota de su jefe.
31. Listar los códigos de los empleados que tienen una línea de pedido superior a 10.000
Bs o que tengan una cuota inferior a 10.000 Bs.
SELECT rep
FROM pedidos
WHERE importe > 10000
UNION
SELECT numemp
FROM empleados
WHERE cuota < 10000;
32. Obtener el importe total de ventas de todos los empleados y el mayor objetivo de las
oficinas asignadas a los empleados:
13
33. Obtener de cada precio unitario el importe total vendido.
34. ¿Cuál es la cuota media y las ventas medias de todos los empleados?
35. Hallar el importe medio de pedidos, el importe total de pedidos y el precio medio de
venta (el precio de venta es el precio unitario en cada pedido).
37. ¿ Cuál es el importe total de los pedidos realizados por el empleado Pedro Roriz?
38. Hallar en la fecha en la que se realizó el primer pedido (suponiendo que en la tabla de
pedidos se tienen todos los pedidos realizados hasta la fecha).
13
40. Listar cuántos empleados están asignados a cada oficina, indicar el número de oficina
y cuántos hay asignados.
41. Para cada empleado, obtener su número, nombre e importe vendido por ese empleado
a cada cliente indicando el número de cliente.
42. Para cada empleado cuyos pedidos suman más de 300.000 Bs, hallar su importe
medio de pedidos. En el resultado indicar el número de empleados y su importe
medio de pedidos.
43. Listar de cada producto, su descripción, precio y cantidad total pedida, incluyendo sólo
los productos cuya cantidad total pedida sea superior al 75% del stock y ordenado
por cantidad total pedida.
44. ¿Cuántas oficinas tienen empleados con ventas superiores a su cuota, no se quiere
saber cuáles sino cuántas hay?
13
45. Listar el número y nombre de los empleados cuya fecha de contrato sea igual a la
primera fecha de todos los pedidos de la empresa.
46. Listar los nombres de los clientes que tienen asignado el representante Alvaro
Jaumes (suponiendo que no pueden haber representantes con el mismo nombre).
SELECT nombre
FROM clientes
WHERE repclie = (SELECT numemp
FROM empleados
WHERE nombre = 'Alvaro Jaumes');
47. Listar los vendedores (numemp, nombre, y nº de oficina) que trabajan en oficinas
"buenas" (las que tienen ventas superiores a su objetivo).
Solución 1:
Solución 2:
Solución 3:
13
48. Listar los vendedores que no trabajan en oficinas dirigidas por el empleado 108.
49. Listar los productos (idfab, idproducto y descripción) para los cuales no se ha recibido
ningún pedido de 25000 Bs o más.
50. Listar los clientes asignados a Ana Bustamante que no han remitido un pedido
superior a 3000 Bs.
51. Listar las oficinas en donde haya un vendedor cuyas ventas representan más del
55% del objetivo de su oficina.
SELECT *
FROM oficinas
WHERE EXISTS (SELECT *
FROM empleados
WHERE empleados.oficina = oficinas.oficina
AND ventas > objetivo * 0.55);
13
52. Listar las oficinas en donde todos los vendedores tienen ventas que superan al
50% del objetivo de la oficina.
Solución 1:
SELECT *
FROM oficinas
WHERE (objetivo * 0.5) <= ALL ( SELECT ventas
FROM empleados
WHERE empleados.oficina =
oficinas.oficina
AND ventas IS NOT NULL);
Solución 2:
SELECT *
FROM oficinas
WHERE (objetivo * .5) <= (SELECT MIN(ventas)
FROM empleados
WHERE empleados.oficina = oficinas.oficina);
53. Listar las oficinas que tengan un objetivo mayor que la suma de las cuotas de
sus vendedores.
SELECT *
FROM oficinas
WHERE objetivo > ( SELECT SUM(cuota)
FROM empleados
WHERE empleados.oficina = oficinas.oficina);
UPDATE productos
SET precio = precio * 1.05
WHERE idfab = 'ACI';
55. Añadir una oficina para la ciudad de Caracas, con el número de oficina 30, con
un objetivo de 100000 y región Centro.
Solución 1:
13
Solución 2:
Solución 3:
UPDATE empleados
SET oficina = 30
WHERE oficina = 21;
14
62. A los empleados de la oficina 30 asignarles la oficina 21.
UPDATE empleados
SET oficina = 21 WHERE oficina = 30;
14
67. Añadir a la definición de clientes la columna limitecredito.
14
Ejercicio 23 - Empresa [19]
Dado el siguiente modelo entidad relación, se pide:
SELECT *
FROM EMP;
SELECT *
FROM DEPT;
3. Obtener todos los datos de los administrativos (su trabajo es, en inglés, ’CLERK’).
SELECT *
FROM EMP
WHERE JOB=’CLERK’;
4. Obtener el nombre y empleo de todos los empleados, ordenado primero por su trabajo
y luego por su salario.
14
5. Obtener los salarios y las comisiones de los empleados del departamento 30, pero
ordenado por comisión.
SELECT SAL, COMM
FROM EMP
WHERE DEPTNO = 30
ORDER BY COMM;
8. Obtener los nombres de los empleados y sus salarios, de forma que no se repitan filas.
10. Listar los empleados que tienen una comisión superior a la mitad de su salario.
SELECT ENAME
FROM EMP
WHERE COMM > SAL/2;
11. Listar los empleados que no tienen comisión, o que la tengan menor o igual que el 25
% de su salario.
SELECT ENAME
FROM EMP
WHERE COMM IS NULL
OR COMM <= (0.25 * SAL);
14
12. Listar el código, salario y comisión de los empleados cuyo código sea mayor que 7500.
14. Muestra el nombre de los empleados que, teniendo un salario superior a 1000, tengan
como jefe al empleado cuyo c´odigo es 7698.
SELECT ENAME
FROM EMP
WHERE SAL > 1000
AND MGR = 7698;
15. Indicar para cada empleado el porcentaje que supone su comisión sobre su salario,
ordenando el resultado por el nombre del mismo.
16. Listar los empleados del departamento 10 cuyo nombre no contiene la cadena LA.
SELECT ENAME
FROM EMP
WHERE DEPTNO = 10
AND ENAME NOT LIKE '%LA%';
17. Obtener los empleados que no son supervisados por ningún otro.
SELECT ENAME
FROM EMP
WHERE MGR IS NULL;
14
18. Obtener los nombres de los departamentos que no sean Ventas (SALES) ni de
investigación (RESEARCH). Ordena el resultado por la localidad del departamento.
SELECT DNAME
FROM DEPT
WHERE DNAME NOT IN ('SALES','RESEARCH')
ORDER BY LOC;
19. Listar el nombre de los empleados y el código del departamento de los administrativos
(CLERK) que no trabajan en el departamento 10, y cuyo salario es superior a 800 Bs,
ordenado por fecha de contratación.
20. Para los empleados que tengan comisión, obtener sus nombres y el cociente entre su
salario y su comisión (excepto cuando la comisión sea cero), ordenando el resultado
por nombre.
21. Listar toda la información sobre los empleados cuyo nombre completo tenga
exactamente 5 caracteres.
SELECT *
FROM EMP
WHERE ENAME LIKE ' ';
22. Igual a la 21, pero para los empleados cuyo nombre tenga al menos cinco letras.
SELECT *
FROM EMP
WHERE ENAME LIKE ' %';
14
23. Hallar los datos de los empleados que, o bien su nombre empieza por A y su salario es
superior a 1000, o bien reciben comisión y trabajan en el departamento 30.
SELECT *
FROM EMP
WHERE (ENAME LIKE 'A%' AND SAL > 1000)
OR (COMM IS NOT NULL AND DEPTNO = 30);
24. Listar el nombre, el salario y el sueldo total de todos los empleados, ordenando el
resultado primero por salario y luego por el sueldo total.
25. Obtener el nombre, salario y la comisión de los empleados que perciben un salario que
está entre la mitad de la comisión y la propia comisión.
26. Listar los nombres y empleos de aquellos empleados cuyo empleo acaba en MAN y cuyo
nombre empieza por A.
27. Listar los nombres y fecha de contratación de aquellos empleados que no son
vendedores (SALESMAN).
28. Para los empleados que tengan como jefe a un empleado con código mayor que el
suyo, obtener los que reciben de salario más de 1000 Bs y menos de 2000 Bs, o que
están en el departamento 30.
14
29. Obtener los empleados que trabajan en Caracas o Valencia.
SELECT ENAME,LOC
FROM EMP E INNER JOIN DEPT D
ON E.DEPTNO = D.DEPTNO
WHERE LOC IN ('Caracas','Valencia');
30. Para cada empleado obtener el nombre del departamento donde trabaja.
SELECT ENAME,DNAME
FROM EMP E INNER JOIN DEPT D
ON E.DEPTNO = D.DEPTNO;
31. Listar los datos de los empleados del departamento de ventas (’SALES’).
14
Ejercicio 24 - Parque Temático [20]
Dado la siguiente definición, se pide:
14
2. Hacer que no puedan haber dos escuelas con el mismo nombre.
ALTER TABLE escuela
ADD CONSTRAINT u_nombre UNIQUE (nombre_escuela);
8. Crear un índice que impida ingresar dos guías con igual nombre y apellido.
10. Actualice la fecha de una reserva que usted seleccione por 23/12/2004.
15
11. Debe realizarse un descuento en el arancel por alumno de $2 para todas las reservas
de más de 10 alumnos.
UPDATE reserva_tipo_visita
SET arancel_por_alumno = arancel_por_alumno - 2
WHERE cantidad_alumnos_reservados > 10 ;
12. Actualice el código de guía de las reservas que tengan asignado al guía 1 por el guía 2.
SELECT *
FROM guia
WHERE nombre_guia LIKE '%Bernardo%' ;
SELECT COUNT(* )
FROM reserva
WHERE fecha_visita_reservada > '20040103' ;
17. Se necesita conocer la cantidad total de alumnos reservados para cada reserva
(agrupadas por reservas).
SELECT numero_reserva,
SUM(cantidad_alumnos_reservados) AS total_reserva
FROM reserva_tipo_visita
GROUP BY numero_reserva ;
15
18. Liste todas las reservas que posee una cantidad total de alumnos reservados mayor a
100.
SELECT numero_reserva,
SUM(cantidad_alumnos_reservados) AS total_reserva
FROM reserva_tipo_visita
GROUP BY numero_reserva
HAVING SUM(cantidad_alumnos_reservados) > 100 ;
19. Muestre las reservas realizadas en las cuales la inasistencia a las visitas sea mayor a 5.
SELECT numero_reserva,
cantidad_alumnos_reservados , cantidad_alumnos_reales
FROM reserva_tipo_visita
WHERE (cantidad_alumnos_reservados - cantidad_alumnos_reales) > 5 ;
20. Obtenga la cantidad de escuelas que visitarán el parque después del '3/6/2004'.
21. Insertar un nuevo guía con el número inmediato consecutivo al máximo existente.
22. Insertar un nuevo tipo de visita con el número inmediato consecutivo al máximo existente
sin utilizar subconsultas.
23. Insertar los datos de la tabla escuela en una nueva tabla, borre los datos de la tabla
escuela. En la nueva tabla realice una actualización de los códigos de escuela
incrementándose en uno. Posteriormente reinsértelos en la tabla escuela y vuelva a la
normalidad los códigos.
15
DELETE FROM ESCUELA ;
UPDATE escuela2 SET codigo_escuela = codigo_escuela + 1 ;
24. . Debido a un feriado inesperado, las fechas de las visitas deben posponerse por un día.
UPDATE reserva
SET fecha_visita_reservada = fecha_visita_reservada + 1 ;
SELECT TOP 1 *
FROM reserva
ORDER BY fecha_visita_reservada DESC, hora_visita_reservada ASC ;
SELECT AVG(cantidad_alumnos_reales),
AVG(cantidad_alumnos_reservados),
AVG(cantidad_alumnos_reservados) - AVG(cantidad_alumnos_reales)
FROM reserva_tipo_visita ;
15
29. Obtener los guías que tengan más de 3 visitas.
30. Listar las escuelas cuyos domicilios sean de calles que empiecen con S, indicando
nombre, domicilio y teléfono. Hacer una versión en la que aparezcan sólo las que tienen
teléfono, y hacer otra en la que aparezca solo las escuelas con domicilio en calles que
empiecen con S y que no tienen ningún teléfono.
V1:
SELECT ESC.Nombre_Escuela, ESC.Domicilio_Escuela, TEL.Telefono_Escuela
FROM escuela ESC INNER JOIN telefono_escuela TEL
ON ESC.Codigo_Escuela = TEL.Codigo_Escuela
WHERE ESC.Domicilio_Escuela LIKE 'S%';
V2:
SELECT ESC.Nombre_Escuela, ESC.Domicilio_Escuela, TEL.Telefono_Escuela
FROM escuela ESC LEFT JOIN telefono_escuela TEL
ON ESC.Codigo_Escuela = TEL.Codigo_Escuela
WHERE ESC.Nombre_Escuela LIKE 'S%'
AND TEL.Codigo_Escuela IS NULL;
31. Listar las reservas mostrando día, nombre de escuela, cantidad de alumnos de reserva
y el nombre del guía.
SELECT RES.Numero_Reserva,
RES.Fecha_Visita_Reservada,
ESC.Nombre_Escuela,
REV.Cantidad_Alumnos_Reservados,
GUI.Nombre_Guia, GUI.Apellido_Guia
FROM guia GUI,
escuela ESC,
reserva RES,
Reserva_Tipo_Visita REV
WHERE ESC.Codigo_Escuela = RES.Codigo_Escuela
AND RES.Numero_Reserva = REV.Numero_Reserva
AND GUI.Codigo_Guia = REV.Codigo_Guia;
32. Listar las reservas, la cantidad total real de alumnos y el valor total (cantidad x
arancel con iva incluido).
15
SELECT REV.Numero_Reserva,
SUM(REV.Cantidad_Alumnos_Reales) AS TOTAL_Alumn_Asistentes,
SUM(REV.Cantidad_Alumnos_Reales * TVI.Arancel_por_Alumno * 1.21)
AS VALOR_TOTAL
FROM tipo_visita TVI INNER JOIN Reserva_Tipo_Visita REV
ON TVI.Codigo_Tipo_Visita = REV.Codigo_Tipo_Visita
GROUP BY REV.Numero_Reserva;
33. Listar las reservas y los nombres de escuelas con valor total mayor a $1.000.
34. Listar las escuelas que fueron atendidas alguna vez por el guía “Eleonora Fernandez”.
SELECT ESC.Nombre_Escuela
FROM escuela ESC,
reserva RES,
guia GUI,
Reserva_Tipo_Visita REV
WHERE ESC.Codigo_Escuela = RES.Codigo_Escuela
AND GUI.Codigo_Guia = REV.Codigo_Guia
AND RES.Numero_Reserva = REV.Numero_Reserva
AND GUI.Nombre_Guia = 'Eleonora'
AND GUI.Apellido_Guia = 'Fernandez'
GROUP BY ESC.Nombre_Escuela;
35. Listar las escuelas que realizaron más de una reserva para el mismo día.
15
GROUP BY ESC.Nombre_Escuela,
RES.Numero_Reserva,
RES.Fecha_Visita_Reservada
HAVING COUNT(RES.Fecha_Visita_Reservada) > 1;
36. Listar los nombres de los guías y la cantidad de visitas para aquellos con más de 3
visitas de 30 personas.
37. Listar las reservas, el día, la cantidad total de alumnos por tipo de visita, el nombre de la
escuela y el nombre del guía.
38. Listar los tipos de visita (Código y Descripción) que han sido asignadas más de 5 veces.
15
39. . Listar los Guías (Apellido y Nombre) que no han sido nunca asignados a una reserva.
40. Listar los Guías (Apellido y Nombre) con visitas de escuelas cuyo nombre no comience
con “E”.
SELECT GUI.Apellido_Guia, GUI.Nombre_Guia
FROM escuela ESC,reserva RES, guia GUI, Reserva_Tipo_Visita REV
WHERE ESC.Codigo_Escuela = RES.Codigo_Escuela
AND GUI.Codigo_Guia = REV.Codigo_Guia
AND RES.Numero_Reserva = REV.Numero_Reserva
AND ESC.Nombre_Escuela NOT LIKE 'E%'
GROUP BY GUI.Apellido_Guia, GUI.Nombre_Guia;
41. Listar las escuelas (Nombre) que tengan visitas en donde la cantidad de alumnos
reservada sea igual a la cantidad de alumnos reales asistentes.
SELECT ESC.Nombre_Escuela
FROM escuela ESC, reserva RES, Reserva_Tipo_Visita REV
WHERE ESC.Codigo_Escuela = RES.Codigo_Escuela
AND REV.Cantidad_Alumnos_Reservados = REV.Cantidad_Alumnos_Reales
AND RES.Numero_Reserva = REV.Numero_Reserva
GROUP BY ESC.Nombre_Escuela;
42. Realizar la Unión de las consultas: Nombres de las escuelas con reservas antes de las
9:00 hs Apellidos de los guías cuyos nombres comiencen con “v”. Ordenar el resultado
en forma descendente
SELECT ESC.Nombre_Escuela
FROM escuela AS ESC ,reserva AS RES
WHERE ESC.Codigo_Escuela = RES.Codigo_Escuela
AND RES.Hora_Visita_Reservada < '9:00:00 AM'
UNION
SELECT GUI.Apellido_Guia
FROM guia GUI
WHERE GUI.Nombre_Guia LIKE 'V%'
ORDER BY 1 DESC;
15
43. Listar los Nombres y Teléfonos de las Escuelas que concurrieron a la visita: “Los
Mamuts en Familia”.
44. Listar para cada grado (sin importar de cual escuela) cuál fue la última vez que
hicieron una visita.
SELECT RVG.Numero_Grado,
MAX(RES.Fecha_Visita_Reservada) AS Ultima_Reserva
FROM reserva RES, Reserva_Por_Grado RVG
WHERE RES.Numero_Reserva = RVG.Numero_Reserva
GROUP BY RVG.Numero_Grado;
45. Insertar en una nueva tabla llamada Guia_Performance los datos del Guía y las sumas
de las cantidades reservadas y reales del año 2003.
15
46. Listar los tipos de visita que fueron guiadas alguna vez por Cristina Zaluzi.
47. Listar los nombres de escuela que visitaron en 2002 pero no lo hicieron en el 2001.
SELECT Nombre_Escuela
FROM escuela esc
WHERE Codigo_Escuela NOT IN (SELECT res1.codigo_escuela
FROM reserva res1
WHERE res1.Fecha_Visita_Reservada)
NOT BETWEEN '01-01-2001' AND '31-12-2001')
AND esc.Codigo_Escuela IN (SELECT res2.codigo_escuela
FROM reserva res2
WHERE YEAR(res2.Fecha_Visita_Reservada)
BETWEEN '01-01-2002' AND '31-12-2002');
48. Listar los guías (codigo, nombre y apellido) que fueron asignados a más de 2 tipos de
visita distintos y con una cantidad total real de alumnos que guiaron, mayor a 200.
15
49. Listar las escuelas que poseen más de 1 reservas con más de 2 tipos de visitas para
cada reserva.
50. Listar el nombre, apellido y código de aquellos guías que, en alguna visita de una
reserva en particular, hayan atendido por lo menos al 40% de los alumnos totales
guiados en todas sus visitas.
51. Listar el nombre y el código de aquellas escuelas que hayan asistido el día en que se
registró la mayor cantidad de alumnos reales.
16
52. Listar el código y nombre de las escuelas cuya fecha de reserva sea igual a la primera
fecha de reserva realizada.
53. Listar las escuelas que visitaron entre los años 2001 y en el 2002.
SELECT esc.Nombre_Escuela
FROM escuela esc
WHERE esc.Codigo_Escuela IN ( SELECT res1.codigo_escuela
FROM reserva res1
WHERE YEAR(res1.Fecha_Visita_Reservada)
BETWEEN 2001 AND 2002 );
54. Listar los guías que tuvieron más de 3 escuelas diferentes y una cantidad total real de
alumnos mayor a 200.
16
55. Listar los nombres y códigos de escuelas con gasto total de todas las visitas mayor a
$1700.
SELECT esc.Nombre_Escuela
FROM escuela esc
WHERE esc.Codigo_Escuela IN ( SELECT res.codigo_escuela
FROM reserva res
INNER JOIN reserva_tipo_visita rev
ON res.numero_reserva = rev.numero_reserva
INNER JOIN tipo_visita tv
ON tv.codigo_tipo_visita =
rev.codigo_tipo_visita
GROUP BY res.codigo_escuela
HAVING
(SUM((tv.Arancel_por_alumno)*
rev.cantidad_alumnos_reales) > 1700) );
56. Listar los guías que hayan tenido en solo un tipo de visita de una reserva en particular
por lo menos el 45% del total de alumnos totales que esa persona atendió.
16
Ejercicio 25 - Vuelta Ciclista [21]
Dado el siguiente modelo relacional, se pide:
Nota: Las claves foráneas en los modelos relacionales presentes en este documento se representan en
cursiva y negrita.
Equipo: contiene los datos de los distintos equipos: nombre (nomequipo) y nombre de su
director (director).
Ciclista: contiene los datos de los ciclistas que componen los distintos equipos: número del
dorsal (dorsal), nombre del ciclista (nombre), edad del ciclista (edad) y nombre del equipo al que
pertenece (nomequipo).
Etapa: contiene los datos de las etapas que componen la vuelta ciclista: número de la
etapa(numetapa) (las etapas se numeran consecutivamente: 1, 2, ...), kilómetros que tiene la
etapa (kms), nombre de la población de donde sale la etapa (salida), nombre de la población
donde está la meta de la etapa (llegada) y número del dorsal del ciclista que ha ganado la etapa
(dorsal). Los atributos salida y llegada están definidos sobre el mismo dominio.
Tramo: contiene los datos de los tramos de montaña que visita la vuelta ciclista: nombre del
tramo(nomtramo), altura máxima del tramo(altura), categoría del tramo: primera, especial, etc.
(categoría), porcentaje que indica la pendiente media del tramo(pendiente), número de la etapa
donde se sube el tramo (numetapa) y número del dorsal que ha ganado el tramo al pasar en
primera posición (dorsal).
Camiseta: contiene los datos de los premios que se otorgan mediante las distintas camisetas:
código de la camiseta (código), clasificación que premia esa camiseta : general, montaña,
etc. (tipo), color de la camiseta asociada (color) e importe del premio que corresponde al ciclista
que termine la vuelta llevando la camiseta (premio).
Lleva: contiene la información sobre qué ciclistas (dorsal) han llevado cada camiseta (código) en
cada una de las etapas (numetapa)
16
1. Nombre y el equipo de aquellos corredores menores de 30 años que han ganado alguna
etapa.
Solución 1:
SELECT DISTINCT nombre, nomequipo
FROM Ciclista C, Etapa E
WHERE edad < 30
AND C.dorsal = E.dorsal;
Solución 2:
SELECT DISTINCT nombre, nomequipo
FROM Ciclista
WHERE edad < 30
AND dorsal IN ( SELECT DISTINCT dorsal FROM Etapa);
2. Nombre y equipo de los corredores mayores de 35 años que han ganado algún tramo.
Solución 1:
SELECT DISTINCT nombre, nomequipo
FROM Ciclista C, Tramo P
WHERE C.dorsal = P.dorsal
AND edad > 35;
Solución 2:
SELECT DISTINCT nombre, nomequipo
FROM Ciclista
WHERE edad > 35
AND dorsal IN (SELECT DISTINCT dorsal FROM Tramo);
3. Datos de las etapas que pasan por algún tramo de montaña y que tienen salida y
llegada en la misma población.
Solución 1:
SELECT DISTINCT E.numetapa, E.kms, E.salida, E.llegada, E.dorsal
FROM Etapa E, Tramo P
WHERE E.numetapa = P.numetapa
AND E.salida = E.llegada;
Solución 2:
SELECT *
FROM Etapa
WHERE salida = llegada
AND numetapa IN ( SELECT numetapa FROM Tramo);
16
4. Poblaciones que tienen la meta de alguna etapa, pero desde las que no se realiza
ninguna salida
Solución 1:
SELECT llegada FROM Etapa
MINUS
SELECT salida FROM Etapa;
Solución 2:
SELECT DISTINCT llegada
FROM Etapa
WHERE llegada NOT IN (SELECT salida FROM Etapa);
5. Nombre y el equipo de los ciclistas que han ganado alguna etapa llevando la camiseta
de color amarillo, mostrando también el número de etapa.
7. Número de las etapas que tienen algún tramos de montaña, indicando cuántos tiene
cada una de ellas.
16
8. Nombre y edad de los ciclistas que han llevado dos o más camisetas en una misma etapa
9. Obtener el nombre y el equipo de los ciclistas que han llevado alguna camiseta o que
han ganado algún tramo.
Solución 1:
SELECT C.nombre, C.nomequipo
FROM Ciclista C, Lleva LL
WHERE C.dorsal = LL.dorsal
UNION
SELECT C.nombre,C.nomequipo
FROM Ciclista C, Tramo P
WHERE C.dorsal = P.dorsal;
Solución 2:
SELECT nombre, nomequipo
FROM Ciclista
WHERE dorsal IN (SELECT dorsal FROM Lleva)
OR dorsal IN (SELECT dorsal FROM Tramo);
10. Obtener los números de las etapas que no tienen tramos de montaña.
Solución 1:
SELECT numetapa FROM Etapa
MINUS
SELECT numetapa FROM Tramo;
Solución 2:
SELECT numetapa
FROM Etapa
WHERE numetapa NOT IN (SELECT numetapa FROM Tramo);
11. Obtener la edad media de los ciclistas que han ganado alguna etapa.
16
12. Obtener el nombre de los tramos de montaña que tienen una altura superior a la
altura media de todos los tramos.
SELECT nompuerto
FROM Tramo
WHERE altura > ( SELECT AVG(altura) FROM Tramo) ;
13. Obtener las poblaciones de salida y de llegada de las etapas donde se encuentran los
puertos con mayor pendiente.
Solución 1:
SELECT DISTINCT salida, llegada
FROM Etapa E, Tramo P
WHERE E.numetapa = P.numetapa
AND P.pendiente = (SELECT MAX(pendiente) FROM Tramo) ;
Solución 2:
SELECT DISTINCT E.salida, E.llegada
FROM Etapa E, Tramo P
WHERE E.numetapa = P.numetapa
AND P.pendiente >= ALL(SELECT pendiente FROM Tramo) ;
14. Obtener el dorsal y el nombre de los ciclistas que han ganado los puertos de mayor
altura.
Solución 1:
SELECT DISTINCT C.dorsal, C.nombre
FROM Ciclista C, tramo P
WHERE C.dorsal = P.dorsal
AND P.altura = (SELECT MAX(altura)FROM tramo) ;
Solución 2:
SELECT DISTINCT C.dorsal,C.nombre
FROM tramo P, Ciclista C
WHERE P.dorsal = C.dorsal
AND P.altura >= ALL(SELECT altura FROM tramo) ;
16
15. Obtener los datos de las etapas cuyos puertos (todos) superan los 1300 metros de altura.
Solución 1:
SELECT E.*
FROM Tramo P, Etapa E
WHERE P.numetapa = E.numetapa
AND P.altura > 1300
MINUS
SELECT E.*
FROM Tramo P, Etapa E
WHERE P.numetapa = E.numetapa
AND P.altura <= 1300 ;
Solución 2:
SELECT DISTINCT E.*
FROM Tramo P, Etapa E
WHERE P.numetapa = E.numetapa
AND P.altura > 1300
AND E.numetapa NOT IN (SELECT numetapa
FROM Tramo
WHERE altura <= 1300) ;
16. Obtener la edad del ciclista más joven, la del más veterano y la media de edad de los
ciclistas que han participado en la vuelta.
17. Obtener el nombre del equipo y el director del ciclista que ha ganado la etapa más larga.
Solución 1:
SELECT director, Q.nomequipo
FROM Etapa E, Ciclista C, Equipo Q
WHERE E.dorsal = C.dorsal
AND C.nomequipo = Q.nomequipo
AND kms = (SELECT MAX(kms) FROM Etapa);
Solución 2:
SELECT TOP(1) director, Q.nomequipo
FROM Etapa E, Ciclista C, Equipo Q
WHERE E.dorsal = C.dorsal
AND C.nomequipo = Q.nomequipo
ORDER BY kms DESC;
16
18. Obtener el dorsal y el nombre de los ciclistas que hayan ganado alguna etapa,
mostrando también el número de etapas que han ganado.
19. Obtener el nombre de los ciclistas que pertenecen a un equipo de más de cinco
ciclistas y que han ganado alguna etapa, indicando también cuántas etapas han
ganado.
20. Nombre y equipo de los ciclistas que han llevado alguna vez camiseta de color amarillo,
indicando durante cuántas etapas lo han llevado.
21. Por cada equipo, color de las camisetas que han llevado sus ciclistas.
16
22. Nombre y equipo del ganador de la vuelta (es decir, el que ha lucido la camiseta amarilla
en la última etapa).
24. Nombre y dorsal de los ciclistas mayores de 30 años que han ganado algún tramo,
junto con el número de tramos que han ganado.
25. Nombre y director de los equipos que, en alguna etapa, sus ciclistas han llevado tres o
más camisetas.
17
26. Nombre de los equipos que sólo tienen ciclistas menores de 28 años.
SELECT nomequipo
FROM Equipo
WHERE nomequipo IN (SELECT nomequipo
FROM Ciclista
WHERE edad < 28)
AND nomequipo NOT IN (SELECT nomequipo
FROM Ciclista
WHERE edad >= 28);
27. Dorsal y nombre del ciclista que ha llevado la camiseta verde durante más etapas.
Solución 1:
SELECT C.dorsal, C.nombre
FROM Ciclista AS C, Lleva AS L, Camiseta AS M
WHERE C.dorsal = L.dorsal
AND M.código = L.código
AND M.color = 'verde’
GROUP BY C.dorsal, C.nombre
HAVING COUNT(*) >= ALL ( SELECT COUNT(*) AS veces
FROM Lleva LL, Camiseta MA
WHERE LL.código = MA.código
AND MA.color = 'verde'
GROUP BY LL.dorsal );
Solución 2:
SELECT TOP(1) dorsal, nombre
FROM Ciclista AS C, Lleva AS L, Maillot AS M
WHERE C.dorsal = L.dorsal
AND M.código = L.código
AND M.color = 'amarillo'
GROUP BY C.dorsal, C.nombre
ORDER BY COUNT(*) DESC;
28. Obtener todos los datos de aquellos ciclistas de los que se desconozca su edad.
SELECT *
FROM Ciclista
WHERE FechaNacimiento IS NULL;
29. Obtener de las camisetas, el tipo y el premio en dólares (está en bolívares) de aquellas
cuyo premio supere los $5000.
17
30. Obtener el número de las etapas donde el nombre de la ciudad de llegada tenga por
segunda letra una B o donde el nombre de la ciudad de salida lleve dos o más E.
SELECT NumEtapa
FROM Etapa
WHERE llegada LIKE '_B%'
OR salida LIKE '%E%E%';
31. Obtener el nombre y la fecha de nacimiento de los ciclistas que pertenezcan a equipos
cuyo nombre contenga la cadena 100%.
17
Ejercicio 26 - Proyectos de Construcción
Dado el siguiente modelo relacional, se pide:
Nota: Las claves foráneas en los modelos relacionales presentes en este documento se representan en
cursiva y negrita.
SELECT nombre
FROM conductor
WHERE categoria = 15;
2. Obtener la descripción de sus proyectos que se hayan realizado durante los días 11 al 15
de septiembre de 2019.
Solución 1:
SELECT descripcion
FROM proyectos
WHERE CodP IN (SELECT CodP
FROM trabajos
WHERE fecha BETWEEN '11-09-2019' AND '15-09-2019');
Solución 2:
SELECT p.descripcion
FROM proyectos p, trabajos t
WHERE p.CodP = t.CodP
AND t.fecha BETWEEN '11-09-2019' AND '15-09-2019';
17
3. Obtener el nombre de los conductores que hayan trabajado con una
Hormigonera, ordenados descendentemente.
Solución 1:
SELECT DISTINCT c.nombre
FROM conductor c, trabajo t, maquina m
WHERE c.codC = t.codC
AND t.codM = m.codM
AND m.nombre = 'Hormigonera'
ORDER BY nombre DESC;
Solución 2:
SELECT nombre
FROM conductor
WHERE CodC IN (SELECT codC
FROM trabajos
WHERE CodM IN (SELECT CodM
FROM maquinas
WHERE nombre = 'HORMIGONERA'))
ORDER BY nombre DESC;
4. Obtener el nombre de los conductores que hayan trabajado con una Hormigonera
en proyectos de la localidad de Caracas.
Solución 1:
SELECT c.nombre
FROM conductor c, trabajos t,maquina m, proyectos p
WHERE c.codC = t.codC
AND t.codM = m.codM
AND t.codP = p.codP
AND m.nombre = 'Hormigonera'
AND p.localidad = 'Caracas';
Solución 2:
SELECT nombre
FROM conductor
WHERE CodC IN (SELECT codC
FROM trabajos
WHERE CodM IN (SELECT CodM
FROM maquinas
WHERE nombre = 'HORMIGONERA')
AND CodP IN (SELECT CodP
FROM proyectos
WHERE localidad = 'Caracas'));
17
5. Obtener el nombre de los conductores y descripción del proyecto, para
aquellos conductores que hayan trabajado con una Hormigonera en proyectos
de Caracas durante los días 12 al 17 de Octubre del 2019.
8. Obtener todos los datos de los proyectos realizados en Vargas o que sean de un
cliente llamado José.
17
9. Obtener los conductores que figuren con más de 200 horas trabajadas.
10. Obtener los empleados que tengan como apellido Pérez y hayan trabajado en
proyectos de localidades diferentes a las suyas.
Solución 1:
SELECT c.nombre
FROM conductor c, trabajos t, proyectos p
WHERE c.codC = t.codC
AND p.codP = t.codP
AND c.nombre LIKE '%Pérez'
AND p.localidad NOT IN (SELECT localidad
FROM conductor
WHERE nombre LIKE '%Pérez');
Solución 2:
SELECT c.nombre
FROM conductor c, trabajos t, proyectos p
WHERE c.nombre LIKE '%Pérez%'
AND p.localidad != c.localidad
AND p.codP = t.codP
AND t.codC = c.codC;
11. Obtener el nombre de los conductores y la localidad del proyecto, para aquellos
conductores que hayan trabajado con máquinas con precio hora comprendido
entre 10000 y 15000 Bs.
17
12. Obtener el nombre y localidad de los conductores, y la localidad del proyecto para
aquellos proyectos que sean de Vargas y en los que no se haya utilizado una máquina
de tipo Excavadora o una máquina de tipo Hormigonera.
13. Obtener el nombre de los conductores, el nombre del cliente y localidad del proyecto, en
los que se haya utilizado la máquina con el menor precio hora.
14. Obtener todos los datos de los proyectos que siempre han utilizado una máquina
de precio por sobre el promedio de éstas.
15. Obtener los proyectos en los que haya trabajado el conductor de categoría más alta
menos dos puntos, con la máquina de precio hora más bajo.
17
16. Obtener por cada uno de los clientes el tiempo total empleado en sus proyectos.
17
Ejercicio 27 - Empresas de envíos [21]
Dado el siguiente modelo relacional, se pide:
La relación S almacena los datos de los proveedores: código (sn), nombre (snombre), estado
(estado) y ciudad donde se ubica cada proveedor (ciudad).
La relación P almacena la información referente a las piezas: código (pn), nombre (pnombre),
color (color), peso (peso) y ciudad donde se almacena cada pieza (ciudad).
Los atributos S.ciudad y P.ciudad están definidos sobre el mismo dominio (nombres de ciudades).
La relación SP almacena los datos sobre los envíos mensuales que cada proveedor realiza
(sn)de cada pieza que suministra (pn). Cada uno de estos envíos contiene un número de
unidades determinado (cant)
SELECT *
FROM P
WHERE color = 'rojo'
AND peso > 15;
17
4. Datos de los proveedores que envían la pieza P1 y cantidad que envían.
5. Nombre de los proveedores que suministran la pieza con código P2, ordenados
alfabéticamente.
6. Nombre de los proveedores que suministran por lo menos una pieza roja.
8. Nombre y cantidad de todas las piezas enviadas por el proveedor con código S3.
9. Nombre de las piezas de color rojo suministradas por los proveedores de la ciudad de
Caracas.
18
10. Número total de unidades de piezas suministradas por cada proveedor.
12. Listado de las piezas cuyo peso supera las 12 unidades y cuyo nombre termina por la
letra o ó por la letra a. De cada pieza hay que mostrar su número, su nombre y su color. El
listado debe aparecer ordenado por el color. Las que sean del mismo color deben salir
ordenadas por peso descendentemente.
18
17. ¿Cuántas piezas son rojas?
21. ¿Cuál es la cantidad media de los envíos del proveedor S1, sin tener en cuenta los de
las piezas P1 y P2?
Solución 1:
SELECT pnombre AS mas_pesada
FROM P
WHERE peso = (SELECT MAX(peso) FROM P);
Solución 2:
SELECT pnombre AS mas_pesada
FROM P WHERE peso >= ALL (SELECT peso FROM P);
SELECT *
FROM SP
WHERE cant = (SELECT MIN(cant)FROM SP);
18
24. ¿Cómo se llaman los proveedores que tienen un estado superior al valor medio de éste?
SELECT snombre
FROM S
WHERE estado > (SELECT AVG(estado) FROM S);
26. Muestra la cantidad media por envío realizada por cada proveedor.
27. Muestra la cantidad media por envío de aquellos proveedores que realizan más de dos
envíos.
28. Para cada ciudad en la que se almacenan piezas, obtener el número de piezas que se
almacenan de cada color distinto.
29. Listado de los proveedores que suministran todas las piezas (sólo el código del
proveedor).
SELECT sn AS proveedores
FROM SP
GROUP BY sn
HAVING COUNT(*) = (SELECT COUNT(*) FROM P);
18
30. Obtener el código de los proveedores que suministran alguna de las piezas
suministradas por el proveedor S2.
SELECT DISTINCT sn
FROM SP
WHERE pn IN ( SELECT pn FROM SP WHERE sn = 'S2');
31. Obtener el código de los proveedores que suministran, al menos, todas las piezas
suministradas el proveedor S2.
32. Obtener el código de los proveedores que suministran, al menos, todas las piezas que
se almacenan en la ciudad de Londres.
SELECT sn
FROM SP, P
WHERE P.pn = SP.pn
AND ciudad = 'Londres'
GROUP BY sn
HAVING COUNT(*) = (SELECT COUNT(*)
FROM P
WHERE ciudad = 'Londres') ;
33. Obtener el nombre y el estado de los proveedores que suministran, al menos, todas las
piezas suministradas por el proveedor S2.
18
34. Obtener el nombre y la ciudad de los proveedores que suministran, al menos, todas las
piezas que se almacenan en la ciudad de Londres.
35. Obtener el nombre de los proveedores que suministran alguna pieza verde.
36. Obtener el nombre de los proveedores que no suministran ninguna pieza verde.
37. Obtener el nombre de las piezas de color rojo suministradas por los proveedores de la
ciudad de Londres.
38. Nombre y código de los proveedores que no suministran la pieza con el código P1 .
18
39. Datos de los proveedores que sólo suministran piezas de color rojo.
SELECT *
FROM S
WHERE sn IN (SELECT sn
FROM SP, P
WHERE SP.pn = P.pn
AND P.color = 'rojo' )
AND sn NOT IN (SELECT sn
FROM SP, P
WHERE SP.pn = P.pn
AND color <> 'rojo');
18
Ejercicio 28 - Titulaciones
Dado el siguiente modelo relacional, se pide:
Nota: Las claves foráneas en los modelos relacionales presentes en este documento se representan en
cursiva y negrita.
SELECT Creditos
FROM ASIGNATURA;
SELECT Nombre,Creditos
FROM ASIGNATURA;
SELECT *
FROM PERSONA;
SELECT SUM(Creditos)
FROM ASIGNATURA;
18
6. Media de coste básico.
SELECT AVG(CosteBasico)
FROM ASIGNATURA;
SELECT MAX(CosteBasico)
FROM ASIGNATURA;
SELECT MIN(CosteBasico)
FROM ASIGNATURA;
SELECT COUNT(CosteBasico)
FROM ASIGNATURA;
SELECT COUNT(DISTINCT(CosteBasico))
FROM ASIGNATURA;
SELECT COUNT(*)
FROM ASIGNATURA;
12. Suma de los créditos de las asignaturas llamando a la columna resultante "TotalCreditos".
14. Nombre y Apellido de las personas nacidas antes del 1 de enero de 1975.
18
16. Nombre de las asignaturas cuyo coste básico esté entre 25 y 35 Bs.
Solución 1:
SELECT Nombre
FROM ASIGNATURA
WHERE CosteBasico >= 25 AND CosteBasico <= 35;
Solución 2:
SELECT Nombre
FROM ASIGNATURA
WHERE CosteBasico BETWEEN 25 AND 35;
SELECT DISTINCT(IdAlumno)
FROM ALUMNO_ASIGNATURA
WHERE IdAsignatura = '150212'
OR IdAsignatura = '130113';
SELECT Nombre
FROM ASIGNATURA
WHERE Cuatrimestre = '2'
AND Creditos != 6;
19. Nombre de las asignaturas cuyo coste básico esté entre 25 y 35 Bs.
SELECT Nombre
FROM ASIGNATURA
WHERE CosteBasico BETWEEN 25 AND 35;
SELECT IdAlumno
FROM ALUMNO_ASIGNATURA
WHERE IdAsignatura IN ('150212', '130113');
21. Nombre y apellido de las personas cuyo apellido comience por 'G'.
SELECT Nombre
FROM ASIGNATURA WHERE IdTitulacion IS NULL;
18
23. Nombre de las asignaturas que tienen dato para el IdTitulacion.
SELECT Nombre
FROM ASIGNATURA
WHERE IdTitulacion IS NOT NULL;
24. Nombre de las asignaturas cuyo coste por crédito sea mayor de 8 Bs.
SELECT Nombre
FROM ASIGNATURA
WHERE (CosteBasico/Creditos) > 8;
26. Mostrar el nombre completo en una columna y la dirección completa en otra columna de
las personas.
SELECT *
FROM PERSONA
ORDER BY Apellido;
28. Datos de las asignaturas del 2º cuatrimestre por orden alfabético de IdTitulacion. Para
cada titulación ordenar por coste mostrando primero las asignaturas más caras y para las
asignaturas del mismo coste mostrar por orden alfabético de nombre de asignatura.
SELECT *
FROM ASIGNATURA
WHERE Cuatrimestre = '2'
ORDER BY IdTitulacion, CosteBasico DESC, Nombre;
19
30. Nombre de asignaturas impartidas por profesores de Caracas.
SELECT Asignatura.Nombre
FROM ASIGNATURA, PROFESOR, PERSONA
WHERE ASIGNATURA.IdProfesor = PROFESOR.IdProfesor
AND PROFESOR.DNI = PERSONA.DNI
AND Ciudad = 'Caracas';
31. Nombre completo (nombre y apellido), en una sóla columna, de los alumnos.
32. DNI, Nombre y Apellido de los alumnos que viven en la Gran Caracas. Como criterio
usar el teléfono.
33. DNI, Nombre y Apellido de los alumnos matriculados en la asignatura "Seguridad Vial".
34. Id de las titulaciones en las que está matriculado el alumno con DNI 20202020A.
Un alumno está matriculado en una titulación si está matriculado en una asignatura
de la titulación.
SELECT DISTINCT(IdTitulacion)
FROM ASIGNATURA, ALUMNO_ASIGNATURA, ALUMNO
WHERE ASIGNATURA.IdAsignatura = ALUMNO_ASIGNATURA.IdAsignatura
AND ALUMNO_ASIGNATURA.IdAlumno = ALUMNO.IdAlumno
AND ALUMNO.DNI = '20202020A';
35. Nombre de las asignaturas en las que está matriculada Rosa García, mostrando también
por cada asignatura, el número de matrícula.
SELECT ASIGNATURA.Nombre,ALUMNO_ASIGNATURA.IdAlumno
FROM PERSONA, ALUMNO, ALUMNO_ASIGNATURA, ASIGNATURA
WHERE PERSONA.DNI = ALUMNO.DNI
AND ALUMNO.IdAlumno = ALUMNO_ASIGNATURA.IdAlumno
19
AND ALUMNO_ASIGNATURA.IdAsignatura = ASIGNATURA.IdAsignatura
AND PERSONA.Nombre = 'Rosa'
AND PERSONA.Apellido = 'García';
36. DNI de los alumnos a los que imparte el profesor Jorge Ruiz.
Solución 1:
SELECT ALUMNO.DNI AS DNI_ALUMNO
FROM PERSONA, ALUMNO, ALUMNO_ASIGNATURA, ASIGNATURA, PROFESOR
WHERE PERSONA.DNI = PROFESOR.DNI
AND ALUMNO.IdAlumno = ALUMNO_ASIGNATURA.IdAlumno
AND ALUMNO_ASIGNATURA.IdAsignatura = ASIGNATURA.IdAsignatura
AND ASIGNATURA.IdProfesor = PROFESOR.IdProfesor
AND PERSONA.Nombre = 'Jorge'
AND PERSONA.Apellido = 'Ruiz';
Solución 2:
SELECT ALUMNO.DNI AS DNI_ALUMNO
FROM ALUMNO, ALUMNO_ASIGNATURA, ASIGNATURA
WHERE ALUMNO.IdAlumno = ALUMNO_ASIGNATURA.IdAlumno
AND ALUMNO_ASIGNATURA.IdAsignatura = ASIGNATURA.IdAsignatura
AND ASIGNATURA.IdProfesor IN (SELECT PROFESOR.IdProfesor
FROM PERSONA, PROFESOR
WHERE PERSONA.DNI = PROFESOR.DNI
AND PERSONA.Nombre = 'Jorge'
AND PERSONA.Apellido = 'Sáenz');
37. ¿ Cuál sería el coste global de cursar la titulación de Bases de Datos si el coste de
cada asignatura fuera incrementado en un 7%?
19
Referencias Bibliográficas
[1]R. Elmasri & S. Navathe. Fundamentos de Sistemas de Bases de Datos. Madrid: Addison
Wesley. Quinta Edición. 2007.
[2]A. Oppel & R. Sheldon. Fundamentos de SQL. México: McGRAW-HILL. Tercera Edicion. 2010.
[3] A relational model of data for large shared data banks “A Relational Model Of Data For Large
Shared Data Banks” (Un modelo relacional de datos para grandes bancos de datos
compartidos), en el diario Communications of the ACM, volumen 13, número 6 ( junio de 1970).
[5] D.D Chamberlain, SEQUEL 2: A Unified Approach to Data Definition, Manipulation, and
Control, IBM Journal of Research and Development. , vol. 20, no. 6, noviembre 1976.
[6]C. Gonzalez. Sistemas de Base de Datos. Editorial Tecnológica de Costa Rica 1996.
[7] C. Coronel, S Morris & P. Rob. Bases de datos diseño, implementación y administración.
México: Cengage Learning. Novena edición. 2011.
[11] G. Quintana, M. Marqués, J. Aliaga & M. Aramburu. Aprende SQL. Castellón de la Plana.
Publicacions de Universitat Jaume. 2010
[12] Guía para la instalación, y utilización del sistema gestionador de bases de datos (DBMS)
postgreSQL. Recuperado de:
http://postgresql-dbms.blogspot.com/p/una-vez-terminada-la-instalacion-del_6441.html
[13] M. Fernández. Guía de ejercicios SQL. Cali: Universidad del Valle. 2012.
19
[16] Algebra relacional y SQL. 2006. Recuperado de:
https://www.academia.edu/7277162/Algebra_Relacional_ejercicios_Resueltos
[20] E. Chinkes, E. Alarcon, L. Coronel, D. Contreras & E. Golmand. Guía de SQL. 2008.
Recuperado de:
https://www.academia.edu/36354931/GUIA_DE_SQL_DDL_DATA_DEFINITION_LANGUAGE_DM
L_DATA_MANIPULATION_LANGUAGE
19