Capítulo 2 - Consultas Básicas y Filtrado de Filas
Capítulo 2 - Consultas Básicas y Filtrado de Filas
Resultados de aprendizaje
Construye consultas desde una única tabla, en las que se filtran filas de la
tabla de origen, se excluyen filas duplicadas y se ordenan las filas resultantes.
Las bases de datos relacionales se construyen para que los usuarios, personas o
aplicaciones software, puedan consultar lo que está almacenado en ellas de forma
sencilla, rápida y precisa. Para esto existe el Lenguaje Estructurado de Consulta o SQL
(acrónimo de la expresión en inglés Structured Query Language) el cual es un lenguaje
de dominio específico que fue creado con base en lo planteado en el modelo relacional
de bases de datos propuesto en 1970 por Edgar Frank Codd, específicamente con la
aplicación del álgebra y el cálculo relacional. Luego se convirtió en un estándar
internacional y en la actualidad está presente en la mayoría de los DBMS comerciales.
En este segundo capítulo se abordan los elementos para dar los primeros pasos en el
uso del lenguaje y resolver necesidades de datos con consultas básicas realizadas
únicamente sobre una tabla. En tal sentido, los resultados de aprendizaje están
centrados en trabajar con la sentencia SELECT, la cual permite, de forma muy sencilla,
solicitarle al DBMS la selección de un conjunto de datos requeridos, obteniendo como
respuesta una tabla.
Bases de datos relacionales para estudiantes de pregrado
Por ejemplo, una instrucción en SQL para realizar una consulta podría solamente
especificar los datos, es decir, las columnas requeridas, la tabla en dónde están dichas
columnas y, si es el caso, la condición que deben cumplir las filas para ser incluidas en
la tabla resultante. El DBMS tomará esa instrucción y determinará, por ejemplo, si es
necesario recorrer una a una las filas de la tabla para identificar aquellas en las que se
almacenan ciertos datos o si puede utilizar alguna estructura de datos que permita la
ejecución de procedimientos para hacer más eficiente el proceso. Esta forma de
operación se representa de forma general en la Figura 2-1.
Las operaciones del lenguaje SQL se agrupan en tres categorías o en tres sub-lenguajes
de acuerdo con la función general que cumplen. El primero reúne a las operaciones
de creación de los objetos de la base de datos y se conoce como el Lenguaje de
Definición de Datos o DDL (acrónimo de la expresión en inglés Data Definition
Language). El segundo, denominado Lenguaje de Manipulación de Datos o DML
(acrónimo de la expresión en inglés Data Manipulation Language), está conformado por
las operaciones con las que se procesan los datos de las tablas para, por ejemplo,
insertar nuevas filas, consultarlos, modificarlos y eliminarlos. El tercero, conocido
como Lenguaje de Control de Datos o DCL (acrónimo de la expresión en inglés Data
Control Language), contiene las operaciones para establecer y controlar quién puede
acceder a la base de datos, a los objetos que la componen y a los datos almacenados.
Los datos esenciales para administrar la colección siguen siendo los correspondientes
a las canciones y a los artistas que las interpretan. Por consiguiente, las tablas Artistas
y Canciones se mantienen, pero adicionándole algunas columnas o modificando el
contenido de otras para reducir la redundancia. Además, se introdujeron dos nuevas
tablas para almacenar los datos de los Álbumes en los cuales estuvieron incluidas las
canciones al momento del lanzamiento y los Géneros musicales que permiten clasificar
tanto a las Canciones como a los Artistas.
En la tabla Artistas se agregó una columna para registrar el año de retiro, es decir,
cuando el solista deja la actividad musical profesional o cuando el grupo se desintegra.
Esta nueva columna permite valores nulos (NULL) para los artistas que no se han
retirado, es decir, que están activos actualmente. También se cambió el contenido de
la columna género principal por un número que corresponde al identificador del
género según lo registrado en la nueva tabla Géneros.
Artistas
identificador nombre año de lanzamiento año de retiro tipo género principal
50001 Carlos Vives 1986 NULL Solista 1
50002 Niche 1979 NULL Grupo 2
50003 Shakira 1990 NULL Solista 3
50004 Binomio de Oro de América 1976 NULL Grupo 1
50005 J Balvin 2006 NULL Solista 4
v
identificador título duración género idioma artista principal álbum original
10001 La tierra del olvido 00:04:25 1 español 50001 900001
10002 Ojos así 00:03:57 3 español 50003 900002
10003 Mi gente 00:03:05 4 español 50005 NULL
10004 Ambiente 00:04:08 4 español 50005 900004
10005 Cali pachanguero 00:04:51 2 español 50002 900005
10006 La creciente 00:03:04 1 español 50004 900006
10007 Sueños de conquista 00:04:02 1 español 50004 900008
10009 Carito 00:03:39 3 español 50001 900009
10011 Una aventura 00:05:16 2 español 50002 900011
10012 Ginza 00:04:39 4 español 50005 NULL
10013 Octavo día 00:04:32 3 español 50003 900002
10014 Quiero verte sonreír 00:03:18 3 español 50001 900009
Géneros
identificador nombre
1 Vallenato
2 Salsa
3 Pop
4 Urbano Latino
Álbumes
identificador título fecha de lanzamiento sello discográfico
900001 La tierra del olvido 25/07/1995 EMI Latin
900002 ¿Dónde están los ladrones? 29/09/1998 Sony Music
900004 Vibras 25/05/2018 Universal
900005 No hay quinto malo NULL Internacional Records
900006 El binomio de oro 03/11/1976 Codiscos
900008 Por lo alto 02/11/1976 Codiscos
900009 Déjame entrar 06/11/2001 EMI Latin
900011 Cielo de tambores 20/12/1990 Codiscos
Teniendo la claridad sobre los elementos que componen la nueva versión de la base
de datos, se iniciará el aprendizaje del SQL utilizando los cuatro elementos de análisis
planteados en el Capítulo I y su equivalencia en el lenguaje. Para esto se propone la
siguiente pregunta que especifica una necesidad de datos que debe ser satisfecha.
Este análisis presenta el escenario más sencillo de consulta de los datos de una tabla
con SQL. Aquí deben obtenerse todas las columnas y todas las filas. No se establecen
filtros ni operaciones sobre los datos. En tal sentido, lo siguiente será escribir la
consulta que deberá ejecutar el DBMS para retornar los datos requeridos. Es preciso
mencionar que este esquema de análisis de cuatro elementos se va interiorizando con
la práctica y su elaboración escrita se vuelve opcional.
Vale recordar que en SQL debe expresarse lo que debe realizar el DBMS sin necesidad
de definir y programar la forma en que debe realizarse. Por consiguiente, para este
caso en concreto debe indicársele al DBMS que entregue una tabla conformada con
los datos almacenados en todas las columnas y todas las filas de la tabla Artistas. El
código SQL para lograr este resultado se presenta en el Script 2-1. El resultado de
esta consulta se presenta en la Tabla 2-5.
Script 2-1
SELECT identificador,
nombre,
"año de lanzamiento",
"año de retiro",
tipo,
"género principal"
FROM Artistas
En el Script 2-1 puede verse que una consulta SQL tiene una estructura y una sintaxis
sencilla. En este caso se utilizan las palabras SELECT y FROM para comunicarle al DBMS
dos puntos necesarios para obtener la respuesta deseada. El primero especifica las
columnas que deben incluirse en la tabla resultante y el segundo define la tabla que
contienen esas columnas. Al hacer una equivalencia con los cuatro elementos de
análisis que se han venido utilizando desde el Capítulo 1, puede verse que el elemento
3, Columnas para mostrar, equivale en SQL a la palabra SELECT, y el elemento 1,
Ubicación de los datos, equivale a la palabra FROM del SQL.
Los nombres de las columnas que tienen espacios en blanco están entre comillas
cumpliendo las reglas de sintaxis del SQL implementado en el DBMS Postgres. En
otros DBMS se utilizan otros símbolos para indicar que el nombre de una columna
incluye espacios en blanco, como es el caso de SQL Server que utiliza corchetes [ ].
Script 2-2
En el SQL puede usarse el carácter * para hacer referencia a todas las columnas de
una tabla. Por lo tanto, el Script 2-3 genera el mismo resultado que el Script 2-1. Usar
el carácter * tiene varias ventajas. Una es que permite reducir significativamente el
tamaño código. También hace que la misma consulta funcione independientemente de
que se agreguen o eliminen columnas de la tabla. Sin embargo, también tiene limitantes
como que no puede alterarse el orden de las columnas en la tabla resultante.
Script 2-3
En las consultas en las que se declara de forma explícita todas las columnas de la tabla
consultada, se tiene la opción de cambiar el orden en que aparecerán las columnas en
la tabla resultante. Para esto, deben ubicarse en el orden deseado dentro de la lista
separada por comas después de la palabra SELECT. El Script 2-4 ejemplifica esto.
Script 2-4
SELECT identificador,
nombre,
tipo,
"género principal",
"año de lanzamiento",
"año de retiro"
FROM Artistas
El resultado de ejecutar el Script 2-4 contendrá los mismos datos obtenidos con el
Script 2-1 , pero con una estructura distinta, tal y como se muestra en la Tabla 2-6.
Tabla 2-6 Resultado de la consulta del Script 2-4
Para resolver las necesidades de datos es muy común que las consultas se limiten a
un subconjunto de columnas. La declaración explícita, después de la palabra SELECT,
de las columnas a incluir también permite que se especifiquen solamente aquellas
columnas requeridas evitando generar resultados con datos innecesarios. Para ilustrar
esto se propone la necesidad expresada en la siguiente pregunta.
Con esto puede proponerse la consulta SQL del Script 2-5 en la que se incluyen
solamente los nombres de las tres columnas requeridas luego de la palabra SELECT.
Estos nombres se presentan separados por coma. En la Tabla 2-7 se presenta el
resultado de ejecutar la consulta.
Script 2-5
SELECT título,
"fecha de lanzamiento",
"sello discográfico"
FROM Álbumes
Una posibilidad que ofrece el SQL para mejorar la presentación de los resultados,
precisar el contenido que se muestra, o eliminar ambigüedades, es la de asignarle un
nombre alternativo o un alias a las columnas que se van a mostrar. Podría ser, por
ejemplo, que quiera mejorarse la presentación del resultado expuesto en la Tabla 2-7.
En lugar de obtener una columna llamada título se podría utilizar la palabra álbum, en
lugar de fecha de lanzamiento el encabezado lanzamiento y en lugar de sello
discográfico la palabra disquera. Para cumplir con este requisito de presentación, la
consulta SQL debe modificarse tal como se muestra en el Script 2-6.
Script 2-6
Puede observarse que hay dos formas de asignar el alias, La primera, de forma
explícita, en la que se utiliza la palabra AS seguida del nombre que va a tener la columna
en la tabla resultante, como es el caso de los alias álbum y lanzamiento. La segunda,
de forma implícita, en la que, simplemente, se escribe el alias luego del nombre de la
columna, como es el caso de la columna sello discográfico y el alias disquera.
En este sentido, lo primero que puede pensarse es escribir una consulta para obtener
la columna tipo de la tabla Artistas, como se muestra en el Script 2-7. Al ejecutarla,
el DBMS genera el resultado mostrado en la Tabla 2-9. La tabla resultante tiene la
columna requerida con los datos almacenados en todas las filas de la tabla.
Script 2-7
SELECT tipo
FROM Artistas
tipo
Solista
Grupo
Solista
Grupo
Solista
Este resultado no puede aceptarse como respuesta a la pregunta porque hay filas
duplicadas. Del análisis directo sobre los datos puede identificarse que la respuesta
correcta a la pregunta debería tener únicamente dos filas, una para el tipo de artista
denominado “Grupo” y otra para el tipo “Solista”. Para estos casos, el SQL proporciona
una forma de eliminar las filas duplicadas y obtener el resultado requerido.
Específicamente, debe utilizarse la palabra DISTINCT, tal y como se presenta en el Script
2-8, generándose el resultado mostrado en la Tabla 2-10.
Script 2-8
SELECT DISTINCT
tipo
FROM Artistas
tipo
Grupo
Solista
La palabra DISTINCT también puede utilizarse en consultas que muestren más de una
columna. En este caso, el DBMS mostrará únicamente las filas con combinaciones
distintas. Para ilustrar esto se abordará la solución a la siguiente pregunta.
La consulta SQL para responder la pregunta se presenta en el Script 2-9, con la cual
se obtiene el resultado presentado en la Tabla 2-11.
Script 2-9
SELECT DISTINCT
género,
idioma
FROM Canciones
género idioma
1 español
2 español
3 español
4 español
Para mostrar esta opción de ordenamiento se tomará como base la consulta del Script
2-6 con la cual se responde la pregunta sobre el título, le fecha de lanzamiento y el
sello discográfico de los álbumes registrados en la colección. En esa consulta se
utilizaron alias de los nombres de las columnas para mejorar la presentación y facilitar
la comprensión de los datos contenidos en la tabla resultante. Sin embargo, los datos
se presentan si un orden definido. Resultaría mucho mejor si los datos aparecen
ordenados, por ejemplo, por el título del álbum de forma alfabética. La consulta SQL
que cumpliría este requisito se presenta en el Script 2-10.
Script 2-10
Script 2-11
En esta pregunta se observan tres hechos diferentes con respecto a las necesidades
de datos abordadas hasta ahora. En primer lugar, se plantea que debe obtenerse una
columna que no está en la tabla original, es decir, una columna derivada. También se
especifica que debe ordenarse el resultado tomando como criterio los datos de dos
columnas y que cada columna tiene un tipo de ordenamiento distinto.
Script 2-12
SELECT nombre,
tipo,
"año de lanzamiento",
2021 - "año de lanzamiento" AS "años de actividad al 2021"
FROM Artistas
ORDER BY tipo,
"años de actividad al 2021" DESC
actividad al 2021. Es así como aparece primero el grupo “Binomio de Oro de América”
pues tiene “45” años y luego el grupo “Niche” puesto que tiene “42” años.
Script 2-13
SELECT título,
género,
duración
FROM Canciones
WHERE duración >= '00:04:00' AND
duración <= '00:05:00'
La expresión se evalúa por cada fila de la tabla de modo que la tabla resultante
contenga únicamente las filas que cumplen la condición porque el resultado de la
evaluación es “Verdadero”. En otras palabras, el proceso que ejecuta el DBMS inicia
tomando cada fila de la tabla y evaluando si cumple la condición. Si la cumple, se incluye
en el conjunto de filas resultante.
Los operadores relacionales, como el operador igual que (=), mayor que (>), menor
que (<), pueden utilizarse para formar todas las expresiones condicionales que se
requieran. En este caso, una de las expresiones condicionales se define para evaluar si
la duración de la canción es menor o igual (<=) a cuatro minutos.
En esta consulta también se observa que las dos expresiones condicionales comparan
el valor de la columna duración con, aparentemente, las cadenas de caracteres
'00:04:00' y '00:05:00'. Sin embargo, lo que realmente sucede es que el DBMS hace
primero una conversión de tipos para transformar estos valores almacenados como
texto en datos del tipo Time y luego es cuando evalúa las expresiones. El resultado de
la ejecución del Script 2-13 es el conjunto de datos presentado en la Tabla 2-15.
Con el operador BETWEEN puede construirse una expresión condicional para, por
ejemplo, determinar si el número 80 está en el rango entre 50 y 200. En otras palabras,
si el valor 80 es mayor e igual que 50 y menor o igual que 200. Para este caso, como
el valor evaluado, es decir el número 80, está entre 50 y 200, la evaluación del
operador BETWEEN genera un resultado TRUE. Si el valor evaluado fuera 49 se obtendría
FALSE y con el valor 50 o el valor 200 se obtendrá TRUE.
Script 2-14
SELECT título,
género,
duración
FROM Canciones
WHERE duración BETWEEN '00:04:00' AND '00:04:51'
Script 2-15
SELECT nombre,
"año de lanzamiento"
FROM Artistas
WHERE tipo = 'Solista' AND
(2021 - "año de lanzamiento" >= 10) AND
(2021 - "año de lanzamiento" <= 20)
Script 2-16
SELECT nombre,
"año de lanzamiento"
FROM Artistas
WHERE tipo = 'Solista' AND
2021 - "año de lanzamiento" BETWEEN 10 AND 20
En esta pregunta se destaca la frase “los artistas del género vallenato o del género pop que
tienen más de cuarenta años de vida artística”. Allí se está indicando una expresión
condicional compuesta en la que el género debe ser igual a “vallenato” o igual a “pop”
y que la diferencia entre el año actual (2021) y el año de lanzamiento del artista debe
ser mayor a cuarenta años. En la Figura 2-9 se presentan las columnas requeridas para
responder la pregunta con los datos almacenados en la tabla Canciones.
Al estar trabajando con una sola tabla, resolver la pregunta implica definir cómo
referirse a los géneros “vallenato” y “pop” pues estos no están almacenados en la tabla
Artistas. En dicha tabla, en lugar de estas cadenas de caracteres se tiene la columna
género principal en la cual se almacena un número entero.
Con esta restricción, la única forma de completar los datos requeridos para escribir
las expresiones condicionales relacionadas con los géneros principales de los artistas
es observar la tabla Géneros para determinar el valor de la columna identificador en
las filas correspondientes a los géneros requeridos. Como se muestra en la Tabla 2-17,
el género “Vallenato” corresponde al identificador “1” y el género “Pop” corresponde
al identificador “3”.
Tabla 2-17 Filas de la tabla Géneros que contienen los identificadores requeridos
Géneros
identificador nombre
1 Vallenato
2 Salsa
3 Pop
4 Urbano Latino
Script 2-17
SELECT nombre,
tipo
FROM Artistas
WHERE (2021 - "año de lanzamiento") > 40 AND
("género principal" = 1 OR
"género principal" = 3)
nombre tipo
Binomio de Oro de América Grupo
Otro operador diseñado para simplificar las tareas de comparación es el operador IN.
Este se utiliza para comprobar que un valor hace parte de una lista de valores. Para
observar el uso de IN se propone la siguiente pregunta.
Script 2-18
SELECT título,
duración
FROM Canciones
WHERE género = 1 OR
género = 2 OR
género = 3
Script 2-19
SELECT título,
duración
FROM Canciones
WHERE género IN (1, 2, 3)
Para resolver la pregunta anterior debe consultarse la tabla Canciones y utilizar las
condiciones definidas en el enunciado para filtrar las filas: 1) Idioma español, 2) el valor
del género podrá ser “Vallenato” (Identificador 1 en la tabla Géneros), “Salsa”
(Identificador 2 en la tabla Géneros) o “Pop” (Identificador 1 en la tabla Géneros) y 3)
el valor de la duración de la canción debe ser mayor o igual a tres minutos y menor
o igual a cuatro minutos. Figura 2-11 se ilustra el análisis realizado y en el Script 2-20
se presenta la consulta que permite responder la pregunta, la cual genera como
resultado el conjunto de datos de la Tabla 2-19.
Script 2-20
SELECT título,
duración
FROM Canciones
WHERE idioma = 'español' AND
género IN (1, 2, 3) AND
duración BETWEEN '00:03:00' AND '00:04:00'
ORDER BY duración DESC
título duración
Ojos así 00:03:57
La creciente 00:03:04
Carito 00:03:39
Quiero verte sonreír 00:03:18
Ojos así 00:03:57
Para caso como este, el SQL tiene el operador LIKE, el cual es utilizado principalmente
para realizar comparaciones de cadenas de texto con dos caracteres comodines, el
porcentaje % y el guion bajo _. El % representa una cadena cualquiera (0 o más
caracteres) y el _ representa un solo carácter. Los caracteres comodines deben
incluirse en la cadena de texto utilizada en la expresión condicional. Por ejemplo, si
se quiere filtrar las filas de los artistas que inician con la letra a, la expresión condicional
sería nombre LIKE 'a%', indicando que debe iniciar con la letra a y luego puede aparecer
cualquier cadena (%). Este operador no es sensible a las mayúsculas.
En esta pregunta se pide incluir aquellos álbumes cuyo título inicia con la letra e. Esto
puede lograrse combinando el operador LIKE con el comodín “%” tal y como se
observa en la consulta del Script 2-21, con la cual se obtiene la Tabla 2-20.
Script 2-21
SELECT título,
"sello discográfico"
FROM Álbumes
WHERE título LIKE 'E%'
Para resolver esta pregunta se requiere trabajar con la tabla Álbumes. Como se
muestra en la Figura 2-13, los datos resultantes están almacenados en las columnas
título y sello discográfico. Además, es necesario realizar un filtrado de filas con
base en los datos de la columna fecha de lanzamiento, específicamente las filas que
almacenan valores NULL.
En este sentido, para evaluar que un valor es NULL se utilizará la palabra reserva IS
acompañada de la palabra NULL, y para indicar que no es NULL, se agregaría la palabra
NOT. En la resolución de la siguiente pregunta se muestra el filtro de valores NULL. En
este caso debe comprobarse de manera directa si el valor de la fecha de lanzamiento
es desconocido, lo cual se logra con la consulta del Script 2-22.
Script 2-22
SELECT título,
"fecha de lanzamiento",
"sello discográfico"
FROM Álbumes
WHERE "fecha de lanzamiento" IS NULL
El trabajo con valores NULL exige un análisis detallado pues pueden generarse errores
de interpretación. Para ilustrar esto se propone la siguiente pregunta.
La respuesta a esta pregunta puede obtenerse con la consulta del Script 2-23. Con
esta consulta se obtendrá como resultado la Tabla 2-21, mostrando los cinco álbumes
que fueron lanzados antes de la fecha indicada en la condición.
Script 2-23
SELECT nombre,
"fecha de lanzamiento",
"sello discográfico"
FROM Álbumes
WHERE "fecha de lanzamiento" <= '31/12/2000'
Sin embargo, este resultado no significa que las demás filas de la tabla correspondan a
álbumes lanzados a partir del año 2001. En otras palabras, es un error asumir que,
dado que la tabla Álbumes tiene ocho filas y el resultado de la consulta del Script 2-23
tiene cinco filas, entonces hay tres álbumes lanzados después del año 2000.
El error de interpretación recae en que la fecha de lanzamiento del álbum “No hay
quinto malo” es desconocida y por ende tiene registrado el valor NULL, por lo tanto,
no es mayor ni menor que '31/12/2000'. En tal sentido, el resultado de la consulta del
Script 2-22 será una tabla con una sola fila, la correspondiente al álbum “No hay quinto
malo” del sello discográfico “Internacional Records”.
• SQL es el lenguaje que utilizan las bases de datos relacionales para permitir la
manipulación de los objetos y de los datos almacenados en ellas.
• DML es el lenguaje utilizado para especificar las consultas de acceso a los datos
y como resultado de una consulta en este lenguaje siempre se obtiene una
estructura en forma de tabla como respuesta.
• La palabra reservada FROM indica desde cuál tabla provienen los datos a utilizar.
• La palabra reservada SELECT se utiliza para especificar las columnas que harán
parte del conjunto de datos resultante.
• La palabra reservada WHERE permite indicar qué condición deben cumplir las
filas que se incluirán en el conjunto resultante.
• Para establecer las condiciones que deben cumplir las filas puede utilizarse
cualquier combinación de operadores y operandos, siempre que la expresión
formado por estos pueda reducirse a Verdadero o Falso.
SELECT título,
idioma
FROM Canciones
WHERE "álbum original" IS NULL AND
idioma = 'español'
SELECT DISTINCT
"sello discográfico"
FROM Álbumes
WHERE
"fecha de lanzamiento" NOT BETWEEN '01/01/1990' AND '31-12-2020'
OR "fecha de lanzamiento" IS NULL
SELECT nombre,
"año de lanzamiento",
tipo
FROM Artistas
WHERE((2021 - "año de lanzamiento") BETWEEN 20 AND 40) AND
"año de retiro" IS NULL
ORDER BY nombre DESC
7. Proponga una consulta SQL que permita responder ¿Cuáles son los sellos
discográficos que han lanzado álbumes el mismo año de la fundación de la
empresa Apple?
SELECT identificador,
nombre,
"año de lanzamiento"
FROM Artistas
WHERE nombre NOT LIKE '%A' OR
nombre NOT LIKE '%E' OR
nombre NOT LIKE '%I' OR
nombre NOT LIKE '%O' OR
nombre NOT LIKE '%U'
SELECT DISTINCT
título
FROM Álbumes
WHERE "fecha de lanzamiento" < '31-10-2000' OR
"fecha de lanzamiento" = NULL
10. Proponga una consulta SQL que permita responder ¿Cuál es el nombre y la
duración de las canciones de genero vallenato, salsa o pop que hayan sido
interpretadas por solistas?