El Lenguaje SQL Funciones en SQL Funciones en SQL • Las funciones realizan una acción tomando argumentos de entrada y retornando un Entrada Salida valor como resultado. Funciones • Son utilizados para: arg 1 Acciones – Realizar cálculos sobre datos. Ejecutadas por la función – Modificar elementos de datos arg 2 individuales. arg N – Manipular salida para grupos de filas. – Formatear fechas y números para su despliegue. – Convertir los tipos de datos de las columnas. Resultados • Varias funciones pueden estar anidadas, como ejemplo, F3(F2(F1(col, arg1), arg2), arg3) Funciones de SQL • Funciones de una sola fila: operan sobre una fila y retornan un resultado por fila. – Caracter: LOWER, UPPER, INITCAP, CONCAT, SUBSTR, LENGTH, INSTR, LPAD. – Número: ROUND, TRUNC, MOD. – Fecha: SYSDATE , MONTHS_BETWEEN, ADD_MONTHS, NEXT_DAY, LAST_DAY, ROUND, TRUNC. – Conversión: TO_CHAR, TO_NUMBER, TO_DATE. • Funciones de múltiples filas: Manipulan grupos de filas y dan un resultado por grupo. Trabajando con fechas • ORACLE almacena las fechas internamente en un formato numérico: siglo, año, mes, día, minutos, segundos. • El formato de fecha por defecto es ‘DD-MM-YY’. • El SYSDATE es una función que retorna la fecha y hora actual. • Se puede sumar o restar un número de días a una fecha. • Se pueden restar dos fechas para obtener el número de días entre ambas. • Para sumar horas a una fecha se divide el número de días entre 24. Conversión de datos implícita • Para las asignaciones, ORACLE convierte automáticamente: DE VARCHAR2 o CHAR VARCHAR2 o CHAR NUMBER DATE A NUMBER DATE VARCHAR2 VARCHAR2 • Para evaluación de expresiones, ORACLE convierte automáticamente: DE A VARCHAR2 o CHAR NUMBER VARCHAR2 o CHAR DATE Conversión de datos explícita • TO_CHAR(numero | fecha, [‘fmt’]) : Convierte un número o fecha a un VARCHAR2 con el modelo de formato fmt. • TO_NUMBER(char) : Convierte una cadena de caracteres que contiene dígitos a número. • TO_DATE(char, [‘fmt’]) : Convierte una cadena de carac-teres que representa una fecha a un valor de fecha de acuerdo al formato fmt especificado. Elementos del formato de fechas YYYY Año en número YEAR Año en letras MM MONTH DY DAY HH24:MI:SS AM Mes en dos dígitos Nombre completo del mes Abreviación de 3 letras del día de la semana Nombre completo del día Horas (militar), minutos y segundos Funciones de agregación Las funciones de agregación operan sobre conjuntos de tuplas para dar un resultado para el conjunto. Ejemplo: Tabla ESTUDIANTE Carnet ApyNombre 92-134111 Miriam Jiménez 94-326423 Angel López 95-098127 Mark Ruiz Indice 4.12 3.75 4.09 "Obtener el índice máximo de todos los estudiantes" 4.12 Funciones de agregación - tipos AVG([DISTINCT | ALL] n) Valor promedio de n, ignorando nulos. COUNT(* | [DISTINCT | ALL] expr) SUM([DISTINCT | ALL] n) Número de filas, en donde la expresión evalúa a un valor diferente de nulo. Si se coloca * cuenta todas las filas incluyendo duplicados y filas con nulos. Máximo valor de la expresión ignorando nulos. Mínimo valor de la expresión ignorando nulos. Desviación estándar de n ignorando nulos. Suma de valores de n ignorando nulos VARIANCE([DISTINCT|ALL] n) Varianza de n ignorando nulos. MAX([DISTINCT | ALL] expr) MIN([DISTINCT | ALL] expr) STDDEV([DISTINCT | ALL] n) •Los tipos de datos para expr son CHAR, VARCHAR2, NUMBER y DATE. •Los tipos de datos para n son numéricos. Sintaxis SELECT columna, funcion_de_agregacion(columna) FROM tabla [WHERE condicion] [ORDER BY columna]; Ejemplo: "Encuentre el índice máximo de los estudiantes de la carrera '001' " SELECT MAX(indice) "indice maximo" FROM ESTUDIANTE WHERE idcarrera = '001'; Consultas particionadas La cláusula GROUP BY se utiliza para dividir las filas de una tabla en particiones. Luego se pueden utilizar funciones de agregación para obtener información sumarizada de cada partición. Ejemplo: Carrera Num Tabla ESTUDIANTE Carnet ApyNombre Indice Carrera 92-134111 Miriam Jiménez 4.12 94-326423 Angel López 3.75 95-098127 Mark Ruiz 4.09 002 001 001 001 002 1 2 "Número de estudiantes por carrera" Consultas particionadas Sintaxis SELECT columna, funcion_de_agregacion(columna) FROM tabla [WHERE condicion] [GROUP BY expresion_de_agrupamiento] [ORDER BY columna] [HAVING condicion_grupo]; La expresión de agrupamiento indica las columnas cuyos valores dan la base para las particiones. Consultas particionadas Ejemplo Ejemplo: "Obtenga el número de estudiantes de cada carrera (el resultado debe tener el nombre de la carrera)" SELECT COUNT(*) "total estudiantes", C.nombre FROM ESTUDIANTE E, CARRERA C WHERE E.idcarrera = C.idcarrera GROUP BY C.nombre Consultas Particionadas Lineamientos Si se incluye una expresión de agrupamiento no se pueden seleccionar también columnas "individuales" a no ser que éstas aparezcan en la cláusula GROUP BY. El ejemplo de la página anterior daría un error si se escribiera así: SELECT COUNT(*) "total estudiantes", E.indice, C.nombre FROM ESTUDIANTE E, CARRERA C WHERE E.idcarrera = C.idcarrera GROUP BY C.nombre Lineamientos • Se puede utilizar la cláusula WHERE para excluir filas antes de dividir en particiones. • Se deben incluir todas las columnas seleccionadas en la cláusula GROUP BY. • Se puede particionar por más de una columna. Cláusula HAVING La cláusula HAVING restringe las particiones que aparecerán en el resultado. Ejemplo: "Obtenga el promedio del índice de los estudiantes de cada carrera con promedio mayor que 3.5 ordenados en orden creciente de promedio“ SELECT idcarrera, AVG(indice) FROM ESTUDIANTE GROUP BY idcarrera HAVING AVG(indice) > 3,5 ORDER BY AVG(indice); Consultas anidadas Ejemplo: • Consulta principal: ¿Cuáles estudiantes tienen un número mayor de créditos inscritos que el estudiante 'Francisco Torres'? • Subconsulta o consulta interna: ¿Cuántos créditos inscritos tiene el estudiante 'Francisco Torres'? Para resolver esta consulta se requieren 2 consultas: una para obtener el número de créditos inscritos del estudiante 'Francisco Torres', y otra para obtener aquellos estudiantes con un número de créditos mayor que el primer resultado. Consultas anidadas - Sintaxis SELECT lista_de_columnas FROM tabla WHERE expr operador (SELECT lista_columnas FROM tabla); • La subconsulta se ejecuta antes que la consulta principal. • El resultado de la subconsulta es utilizado por la consulta principal. Consultas anidadas - Ejemplo El ejemplo anterior se expresa de la siguiente manera: SELECT carnet, apynombre FROM ESTUDIANTE WHERE credins > (SELECT credins FROM ESTUDIANTE WHERE apynombre = 'Francisco Torres'); Consultas anidadas Lineamientos • Las subconsultas van encerradas entre paréntesis. • Las subconsultas deben colocarse al lado derecho del operador de comparación. • Use operadores de "una sola fila" para subconsultas de una sola fila. El ejemplo anterior tiene una subconsulta de una sola fila. • Use operadores de "múltiples filas" para subconsultas que den como resultado múltiples filas. Lineamientos - Ejemplo Ejemplo: "Obtenga los profesores que dictan al menos una de las asignaturas dictadas por 'Marta Medina' " – Subconsulta de varias filas: Obtenga las asignaturas dictadas por 'Marta Medina'. Consultas anidadas Operadores • Los operadores de comparación para subconsultas de una sola fila son =, >, >=, <, <=, <>. • Los operadores de comparación para subconsultas de múltiples filas son: Operador IN Significado Igual a cualquier elemento de la lista. ANY Compara el valor con cada uno de los elementos retornados por la subconsulta. ALL Compara el valor con todos los valores retornados por la subconsulta. Ejemplo de subconsulta de múltiples filas El ejemplo anterior se expresa de la siguiente manera: SELECT nomprof FROM SECCION WHERE codasig IN (SELECT codasig FROM SECCION WHERE nomprof = 'Marta Medina'); Vistas • Una vista representa un subconjunto lógico de los datos de una o más tablas. Carnet ApyNombre Indice Carrera 92-134111 Miriam Jiménez 4.12 94-326423 Angel López 3.75 95-098127 Mark Ruiz 4.09 002 001 001 Vista de "estudiantes de la carrera '001' " Razones para utilizar vistas • • • • Restringen el acceso a la Base de Datos. Simplifican consultas complejas. Permiten la independencia de los datos. Presentan diferentes visiones de los mismos datos. Vistas - Simples y complejas Característica Vistas Simples Vistas Complejas Número de tablas Una Una o más Contienen funciones Contienen particiones Son actualizables No Sí No Sí Sí No siempre Vistas - Sintaxis • Para crear una vista se coloca una subconsulta dentro de la instrucción CREATE VIEW. CREATE [OR REPLACE] [FORCE | NOFORCE] VIEW vista [(alias[, alias] ....)] AS subconsulta [WITH CHECK OPTION [CONSTRAINT restriccion]] Vistas - Sintaxis • FORCE crea la vista aunque no existan las tablas bases. • Los alias permiten crear nombres de columnas para las vistas. • WITH CHECK OPTION especifica que solamente las tuplas que sean accesibles a través de la vista pueden ser eliminadas o actualizadas. • CONSTRAINT permite asignar un nombre a la restricción del CHECK OPTION. Vistas - ejemplo "Crear una vista con los carnet y apellidos y nombres de los estudiantes de cada asignatura" CREATE VIEW LISTA_EST AS SELECT A.codasig, A.carnet, apynombre FROM ASIGNA A, ESTUDIANTE E WHERE A.carnet = E.carnet; "Obtener los carnets, apellidos y nombres de los estudiantes de la asignatura 'AA0001'" SELECT carnet FROM LISTA_EST WHERE codasig = 'AA0001'; Inserción con subconsulta INSERT INTO nombre_tabla subconsulta; Ejemplo: “Inserte a todos los empleados que son gerentes en una nueva tabla de gerentes” INSERT INTO GERENTES(idger, nombre, salario, fechaingreso) SELECT idemp, nombre, sal, fechaingreso FROM EMP WHERE cargo = ‘gerente’; Modificación con subconsulta UPDATE nombre_tabla SET columna = subconsulta WHERE expresion comp subconsulta Ejemplo: “Actualice la tabla de empleados para que todas las tuplas que tengan el mismo cargo que el empleado ‘12345’, trabajen en el mismo departamento” UPDATE EMP SET iddpto = (SELECT iddpto FROM EMP WHERE idemp = ‘12345’) WHERE cargo = (SELECT cargo FROM EMP WHERE idemp = ‘12345’); Eliminación con subconsulta DELETE FROM nombre_tabla WHERE expresion comp subconsulta; Ejemplo: “Borre todos los empleados del departamento de ‘ventas’” DELETE FROM EMP E WHERE E.iddpto = (SELECT D.iddpto FROM DPTO D WHERE nombre = ‘ventas’);